Compare commits
60 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 3554747a67 | |||
| 62968dd437 | |||
| c660fac524 | |||
| 431a69e357 | |||
| f4fcc07288 | |||
| a38cc4d5cb | |||
| 1528d458d9 | |||
| 9e937776ac | |||
| a8aebdd01f | |||
| 998ed87029 | |||
| 279b3f8d9a | |||
| 738a506b6d | |||
| 0ddecdda1f | |||
| 94a22907e2 | |||
| d22a0aad0c | |||
| 9e035f3818 | |||
| 99a810458a | |||
| 2806578126 | |||
| 882e9a6623 | |||
| 14c156e351 | |||
| cd2151332e | |||
| 53bbca3779 | |||
| 51f4ac467e | |||
| 81427a7f9e | |||
| faadfb28b3 | |||
| 6bfe0bed35 | |||
| 6e4d5b853f | |||
| 0ebe23b482 | |||
| abbde5861a | |||
| b78d4349a7 | |||
| 3c1d3234b8 | |||
|
|
79baaae8e7 | ||
| 79289662ed | |||
| 89a2985ad8 | |||
| 1f0a521a87 | |||
| 8a0e43c38c | |||
| ac9022f585 | |||
| 314dbbbeaf | |||
| f13e09910d | |||
| 67b9511afe | |||
| 510c477468 | |||
| 697fcc18ab | |||
| 89ff08b3f2 | |||
| 9417585cd9 | |||
| f794bb5455 | |||
| bb7a5326cd | |||
| a998b2a44e | |||
| a69eb4296f | |||
| 727af5a5b9 | |||
| d545dd8219 | |||
| 29e385ab4b | |||
| 5c63e30b84 | |||
| 5187c677f1 | |||
| 1d43314efd | |||
| 91ef8c69db | |||
| f24251af82 | |||
| ed6e0138e6 | |||
| 4362cdb396 | |||
| 8146680b53 | |||
| 27aa2cfa1f |
6
.github/workflows/cd.yml
vendored
6
.github/workflows/cd.yml
vendored
@@ -1,13 +1,13 @@
|
||||
name: Continuous Deployment
|
||||
on:
|
||||
schedule:
|
||||
- cron: '15 6 * * *'
|
||||
- cron: '15 4 * * *'
|
||||
workflow_dispatch:
|
||||
|
||||
env:
|
||||
DOTNET_NOLOGO: true
|
||||
DOTNET_CLI_TELEMETRY_OPTOUT: false
|
||||
GIT_LFS_PULL_OPTIONS: '-c lfs.concurrenttransfers=1 -c lfs.transfer.maxretries=2 -c http.version="HTTP/1.1" -c lfs.activitytimeout=60'
|
||||
GIT_LFS_PULL_OPTIONS: '-c lfs.concurrenttransfers=10 -c lfs.transfer.maxretries=2'
|
||||
|
||||
jobs:
|
||||
|
||||
@@ -84,7 +84,7 @@ jobs:
|
||||
- name: Checkout LFS
|
||||
run: |
|
||||
git lfs version
|
||||
git ${{ env.GIT_LFS_PULL_OPTIONS }} lfs pull
|
||||
GIT_TRACE=1 GIT_TRANSFER_TRACE=1 git ${{ env.GIT_LFS_PULL_OPTIONS }} lfs pull
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
sudo apt-get install libx11-dev libxcursor-dev libxinerama-dev build-essential gettext libtool libtool-bin libpulse-dev libasound2-dev libjack-dev portaudio19-dev
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
# Redirect to our own Git LFS server
|
||||
[lfs]
|
||||
#url="https://gitlab.flaxengine.com/flax/flaxengine.git/info/lfs"
|
||||
locksverify = false
|
||||
locksverify = false
|
||||
|
||||
BIN
Content/Editor/Camera/M_Camera.flax
(Stored with Git LFS)
BIN
Content/Editor/Camera/M_Camera.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/CubeTexturePreviewMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/CubeTexturePreviewMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/DebugMaterials/DDGIDebugProbes.flax
(Stored with Git LFS)
BIN
Content/Editor/DebugMaterials/DDGIDebugProbes.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/DebugMaterials/SingleColor/Decal.flax
(Stored with Git LFS)
BIN
Content/Editor/DebugMaterials/SingleColor/Decal.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/DebugMaterials/SingleColor/Particle.flax
(Stored with Git LFS)
BIN
Content/Editor/DebugMaterials/SingleColor/Particle.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/DebugMaterials/SingleColor/Surface.flax
(Stored with Git LFS)
BIN
Content/Editor/DebugMaterials/SingleColor/Surface.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/DebugMaterials/SingleColor/SurfaceAdditive.flax
(Stored with Git LFS)
BIN
Content/Editor/DebugMaterials/SingleColor/SurfaceAdditive.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/DebugMaterials/SingleColor/Terrain.flax
(Stored with Git LFS)
BIN
Content/Editor/DebugMaterials/SingleColor/Terrain.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/DefaultFontMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/DefaultFontMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Gizmo/FoliageBrushMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/Gizmo/FoliageBrushMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Gizmo/Material.flax
(Stored with Git LFS)
BIN
Content/Editor/Gizmo/Material.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Gizmo/MaterialWire.flax
(Stored with Git LFS)
BIN
Content/Editor/Gizmo/MaterialWire.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Gizmo/SelectionOutlineMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/Gizmo/SelectionOutlineMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Gizmo/VertexColorsPreviewMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/Gizmo/VertexColorsPreviewMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Highlight Material.flax
(Stored with Git LFS)
BIN
Content/Editor/Highlight Material.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Icons/IconsMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/Icons/IconsMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/IesProfilePreviewMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/IesProfilePreviewMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Particles/Particle Material Color.flax
(Stored with Git LFS)
BIN
Content/Editor/Particles/Particle Material Color.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Particles/Smoke Material.flax
(Stored with Git LFS)
BIN
Content/Editor/Particles/Smoke Material.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/SpriteMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/SpriteMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Terrain/Circle Brush Material.flax
(Stored with Git LFS)
BIN
Content/Editor/Terrain/Circle Brush Material.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Terrain/Highlight Terrain Material.flax
(Stored with Git LFS)
BIN
Content/Editor/Terrain/Highlight Terrain Material.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/TexturePreviewMaterial.flax
(Stored with Git LFS)
BIN
Content/Editor/TexturePreviewMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Editor/Wires Debug Material.flax
(Stored with Git LFS)
BIN
Content/Editor/Wires Debug Material.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Engine/DefaultDeformableMaterial.flax
(Stored with Git LFS)
BIN
Content/Engine/DefaultDeformableMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Engine/DefaultMaterial.flax
(Stored with Git LFS)
BIN
Content/Engine/DefaultMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Engine/DefaultRadialMenu.flax
(Stored with Git LFS)
BIN
Content/Engine/DefaultRadialMenu.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Engine/DefaultTerrainMaterial.flax
(Stored with Git LFS)
BIN
Content/Engine/DefaultTerrainMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Engine/SingleColorMaterial.flax
(Stored with Git LFS)
BIN
Content/Engine/SingleColorMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Engine/SkyboxMaterial.flax
(Stored with Git LFS)
BIN
Content/Engine/SkyboxMaterial.flax
(Stored with Git LFS)
Binary file not shown.
BIN
Content/Shaders/Editor/Grid.flax
(Stored with Git LFS)
BIN
Content/Shaders/Editor/Grid.flax
(Stored with Git LFS)
Binary file not shown.
@@ -15,7 +15,7 @@ if errorlevel 1 goto BuildToolFailed
|
||||
|
||||
:: Build bindings for all editor configurations
|
||||
echo Building C# bindings...
|
||||
Binaries\Tools\Flax.Build.exe -build -BuildBindingsOnly -arch=x64 -platform=Windows --buildTargets=FlaxEditor,FlaxGame
|
||||
Binaries\Tools\Flax.Build.exe -build -BuildBindingsOnly -arch=x64 -platform=Windows --buildTargets=FlaxEditor
|
||||
|
||||
popd
|
||||
echo Done!
|
||||
|
||||
@@ -14,4 +14,4 @@ bash ./Development/Scripts/Mac/CallBuildTool.sh --genproject "$@"
|
||||
# Build bindings for all editor configurations
|
||||
echo Building C# bindings...
|
||||
# TODO: Detect the correct architecture here
|
||||
Binaries/Tools/Flax.Build -build -BuildBindingsOnly -arch=ARM64 -platform=Mac --buildTargets=FlaxEditor,FlaxGame
|
||||
Binaries/Tools/Flax.Build -build -BuildBindingsOnly -arch=ARM64 -platform=Mac --buildTargets=FlaxEditor
|
||||
|
||||
@@ -14,4 +14,4 @@ bash ./Development/Scripts/Linux/CallBuildTool.sh --genproject "$@"
|
||||
# Build bindings for all editor configurations
|
||||
echo Building C# bindings...
|
||||
# TODO: Detect the correct architecture here
|
||||
Binaries/Tools/Flax.Build -build -BuildBindingsOnly -arch=x64 -platform=Linux --buildTargets=FlaxEditor,FlaxGame
|
||||
Binaries/Tools/Flax.Build -build -BuildBindingsOnly -arch=x64 -platform=Linux --buildTargets=FlaxEditor
|
||||
|
||||
@@ -1,11 +1,9 @@
|
||||
// Copyright (c) 2012-2024 Wojciech Figat. All rights reserved.
|
||||
|
||||
using System;
|
||||
using System.Linq;
|
||||
using FlaxEditor.Content.Create;
|
||||
using FlaxEditor.CustomEditors;
|
||||
using FlaxEditor.CustomEditors.Editors;
|
||||
using FlaxEditor.Scripting;
|
||||
using FlaxEditor.Windows;
|
||||
using FlaxEditor.Windows.Assets;
|
||||
using FlaxEngine;
|
||||
@@ -86,67 +84,18 @@ namespace FlaxEditor.Content
|
||||
|
||||
if (_element != null)
|
||||
{
|
||||
_element.CustomControl.CheckValid += OnCheckValidJsonAssetType;
|
||||
// Define the rule for the types that can be used to create a json data asset
|
||||
_element.CustomControl.CheckValid += type =>
|
||||
type.Type != null &&
|
||||
type.IsClass &&
|
||||
type.Type.IsVisible &&
|
||||
!type.IsAbstract &&
|
||||
!type.IsGenericType &&
|
||||
type.Type.GetConstructor(Type.EmptyTypes) != null &&
|
||||
!typeof(FlaxEngine.GUI.Control).IsAssignableFrom(type.Type) &&
|
||||
!typeof(FlaxEngine.Object).IsAssignableFrom(type.Type);
|
||||
}
|
||||
}
|
||||
|
||||
private static Type[] BlacklistedClasses =
|
||||
[
|
||||
typeof(System.Attribute),
|
||||
typeof(FlaxEngine.Object),
|
||||
typeof(FlaxEngine.GUI.Control),
|
||||
];
|
||||
|
||||
private static Type[] BlacklistedStructs =
|
||||
[
|
||||
typeof(Float2),
|
||||
typeof(Float3),
|
||||
typeof(Float4),
|
||||
typeof(Double2),
|
||||
typeof(Double3),
|
||||
typeof(Double4),
|
||||
typeof(Vector2),
|
||||
typeof(Vector3),
|
||||
typeof(Vector4),
|
||||
typeof(Half2),
|
||||
typeof(Half3),
|
||||
typeof(Half4),
|
||||
typeof(Int2),
|
||||
typeof(Int3),
|
||||
typeof(Int4),
|
||||
typeof(Transform),
|
||||
typeof(Quaternion),
|
||||
typeof(BoundingBox),
|
||||
typeof(BoundingSphere),
|
||||
typeof(BoundingFrustum),
|
||||
typeof(Ray),
|
||||
typeof(Plane),
|
||||
typeof(Matrix),
|
||||
typeof(Color),
|
||||
typeof(Color32),
|
||||
typeof(FloatR11G11B10),
|
||||
typeof(FloatR10G10B10A2),
|
||||
typeof(FlaxEngine.Half),
|
||||
];
|
||||
|
||||
private static bool OnCheckValidJsonAssetType(ScriptType type)
|
||||
{
|
||||
// Define the rule for the types that can be used to create a json data asset
|
||||
var mType = type.Type;
|
||||
if (mType == null ||
|
||||
type.IsAbstract ||
|
||||
type.IsStatic ||
|
||||
type.IsGenericType ||
|
||||
!mType.IsVisible)
|
||||
return false;
|
||||
if (type.IsClass)
|
||||
return mType.GetConstructor(Type.EmptyTypes) != null && BlacklistedClasses.FirstOrDefault(x => x.IsAssignableFrom(mType)) == null;
|
||||
if (type.IsStructure)
|
||||
return !type.IsPrimitive &&
|
||||
!type.IsVoid &&
|
||||
!BlacklistedStructs.Contains(mType);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -226,7 +175,7 @@ namespace FlaxEditor.Content
|
||||
{
|
||||
_thumbnail = SpriteHandle.Invalid;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Constructor with overriden thumbnail.
|
||||
/// </summary>
|
||||
@@ -247,7 +196,7 @@ namespace FlaxEditor.Content
|
||||
{
|
||||
Editor.SaveJsonAsset(outputPath, new T());
|
||||
}
|
||||
|
||||
|
||||
/// <inheritdoc />
|
||||
public override AssetItem ConstructItem(string path, string typeName, ref Guid id)
|
||||
{
|
||||
|
||||
@@ -496,7 +496,7 @@ namespace FlaxEditor.Content.Thumbnails
|
||||
// Prepare requests
|
||||
bool isAnyReady = false;
|
||||
int checks = Mathf.Min(10, _requests.Count);
|
||||
for (int i = 0; i < checks && i < _requests.Count; i++)
|
||||
for (int i = 0; i < checks; i++)
|
||||
{
|
||||
var request = _requests[i];
|
||||
try
|
||||
|
||||
@@ -1277,8 +1277,6 @@ bool CookAssetsStep::Perform(CookingData& data)
|
||||
assetStats.Count++;
|
||||
assetStats.ContentSize += FileSystem::GetFileSize(cookedFilePath);
|
||||
|
||||
LOG(Info, "Cooked size of {0}: {1}KB", assetId, (FileSystem::GetFileSize(cookedFilePath) / (1024)));
|
||||
|
||||
if (packageBuilder.Add(data, i->Value, cookedFilePath))
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -415,9 +415,9 @@ bool DeployDataStep::Perform(CookingData& data)
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/NormalTexture"));
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/BlackTexture"));
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/WhiteTexture"));
|
||||
//data.AddRootEngineAsset(TEXT("Engine/Textures/DefaultLensStarburst"));
|
||||
//data.AddRootEngineAsset(TEXT("Engine/Textures/DefaultLensColor"));
|
||||
//data.AddRootEngineAsset(TEXT("Engine/Textures/DefaultLensDirt"));
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/DefaultLensStarburst"));
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/DefaultLensColor"));
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/DefaultLensDirt"));
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/Bokeh/Circle"));
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/Bokeh/Hexagon"));
|
||||
data.AddRootEngineAsset(TEXT("Engine/Textures/Bokeh/Octagon"));
|
||||
|
||||
@@ -195,15 +195,6 @@ namespace FlaxEditor.CustomEditors
|
||||
Presenter.AfterLayout?.Invoke(layout);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void Deinitialize()
|
||||
{
|
||||
Editor = null;
|
||||
_overrideEditor = null;
|
||||
|
||||
base.Deinitialize();
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void OnModified()
|
||||
{
|
||||
|
||||
@@ -68,16 +68,12 @@ namespace FlaxEditor.CustomEditors.Dedicated
|
||||
// Use default prefab instance as a reference for the editor
|
||||
Values.SetReferenceValue(prefabInstance);
|
||||
|
||||
// Display prefab UI (when displaying object inside Prefab Window then display only nested prefabs)
|
||||
var prefabId = prefab.ID;
|
||||
Editor.GetPrefabNestedObject(ref prefabId, ref prefabObjectId, out var nestedPrefabId, out var nestedPrefabObjectId);
|
||||
var nestedPrefab = FlaxEngine.Content.Load<Prefab>(nestedPrefabId);
|
||||
var panel = layout.CustomContainer<UniformGridPanel>();
|
||||
panel.CustomControl.Height = 20.0f;
|
||||
panel.CustomControl.SlotsVertically = 1;
|
||||
if (Presenter == Editor.Instance.Windows.PropertiesWin.Presenter || nestedPrefab)
|
||||
if (Presenter == Editor.Instance.Windows.PropertiesWin.Presenter)
|
||||
{
|
||||
var targetPrefab = nestedPrefab ?? prefab;
|
||||
// Add some UI
|
||||
var panel = layout.CustomContainer<UniformGridPanel>();
|
||||
panel.CustomControl.Height = 20.0f;
|
||||
panel.CustomControl.SlotsVertically = 1;
|
||||
panel.CustomControl.SlotsHorizontally = 3;
|
||||
|
||||
// Selecting actor prefab asset
|
||||
@@ -85,21 +81,17 @@ namespace FlaxEditor.CustomEditors.Dedicated
|
||||
selectPrefab.Button.Clicked += () =>
|
||||
{
|
||||
Editor.Instance.Windows.ContentWin.ClearItemsSearch();
|
||||
Editor.Instance.Windows.ContentWin.Select(targetPrefab);
|
||||
Editor.Instance.Windows.ContentWin.Select(prefab);
|
||||
};
|
||||
|
||||
// Edit selected prefab asset
|
||||
var editPrefab = panel.Button("Edit Prefab");
|
||||
editPrefab.Button.Clicked += () => Editor.Instance.Windows.ContentWin.Open(Editor.Instance.ContentDatabase.FindAsset(targetPrefab.ID));
|
||||
}
|
||||
else
|
||||
{
|
||||
panel.CustomControl.SlotsHorizontally = 1;
|
||||
}
|
||||
editPrefab.Button.Clicked += () => Editor.Instance.Windows.ContentWin.Open(Editor.Instance.ContentDatabase.FindAsset(prefab.ID));
|
||||
|
||||
// Viewing changes applied to this actor
|
||||
var viewChanges = panel.Button("View Changes");
|
||||
viewChanges.Button.Clicked += () => ViewChanges(viewChanges.Button, new Float2(0.0f, 20.0f));
|
||||
// Viewing changes applied to this actor
|
||||
var viewChanges = panel.Button("View Changes");
|
||||
viewChanges.Button.Clicked += () => ViewChanges(viewChanges.Button, new Float2(0.0f, 20.0f));
|
||||
}
|
||||
|
||||
// Link event to update editor on prefab apply
|
||||
_linkedPrefabId = prefab.ID;
|
||||
@@ -206,7 +198,7 @@ namespace FlaxEditor.CustomEditors.Dedicated
|
||||
if (_linkedPrefabId != Guid.Empty)
|
||||
{
|
||||
_linkedPrefabId = Guid.Empty;
|
||||
Editor.Instance.Prefabs.PrefabApplying -= OnPrefabApplying;
|
||||
Editor.Instance.Prefabs.PrefabApplied -= OnPrefabApplying;
|
||||
Editor.Instance.Prefabs.PrefabApplied -= OnPrefabApplied;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,23 +15,13 @@ namespace FlaxEditor.CustomEditors.Dedicated
|
||||
private int _firstTimeShow;
|
||||
private BezierCurveEditor<T> _curve;
|
||||
private Splitter _splitter;
|
||||
private string _heightCachedPath;
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void Initialize(LayoutElementsContainer layout)
|
||||
{
|
||||
var item = layout.CustomContainer<BezierCurveEditor<T>>();
|
||||
_curve = item.CustomControl;
|
||||
var height = 120.0f;
|
||||
var presenter = Presenter;
|
||||
if (presenter != null && (presenter.Features & FeatureFlags.CacheExpandedGroups) != 0)
|
||||
{
|
||||
// Try to restore curve height
|
||||
_heightCachedPath = layout.GetLayoutCachePath("Height");
|
||||
if (Editor.Instance.ProjectCache.TryGetCustomData(_heightCachedPath, out float cachedHeight) && cachedHeight > 10.0f)
|
||||
height = cachedHeight;
|
||||
}
|
||||
_curve.Height = height;
|
||||
_curve.Height = 120.0f;
|
||||
_curve.Edited += OnCurveEdited;
|
||||
_firstTimeShow = 4; // For some weird reason it needs several frames of warmup (probably due to sliders smoothing)
|
||||
_splitter = new Splitter
|
||||
@@ -55,11 +45,7 @@ namespace FlaxEditor.CustomEditors.Dedicated
|
||||
|
||||
private void OnSplitterMoved(Float2 location)
|
||||
{
|
||||
_curve.Height = Mathf.Clamp(_splitter.PointToParent(location).Y, 50.0f, 1000.0f);
|
||||
|
||||
// Cache curve height
|
||||
if (_heightCachedPath != null)
|
||||
Editor.Instance.ProjectCache.SetCustomData(_heightCachedPath, _curve.Height);
|
||||
_curve.Height = Mathf.Clamp(_splitter.PointToParent(location).Y, 50.0f, 1000.0f);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
@@ -147,23 +133,13 @@ namespace FlaxEditor.CustomEditors.Dedicated
|
||||
private int _firstTimeShow;
|
||||
private LinearCurveEditor<T> _curve;
|
||||
private Splitter _splitter;
|
||||
private string _heightCachedPath;
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void Initialize(LayoutElementsContainer layout)
|
||||
{
|
||||
var item = layout.CustomContainer<LinearCurveEditor<T>>();
|
||||
_curve = item.CustomControl;
|
||||
var height = 120.0f;
|
||||
var presenter = Presenter;
|
||||
if (presenter != null && (presenter.Features & FeatureFlags.CacheExpandedGroups) != 0)
|
||||
{
|
||||
// Try to restore curve height
|
||||
_heightCachedPath = layout.GetLayoutCachePath("Height");
|
||||
if (Editor.Instance.ProjectCache.TryGetCustomData(_heightCachedPath, out float cachedHeight) && cachedHeight > 10.0f)
|
||||
height = cachedHeight;
|
||||
}
|
||||
_curve.Height = height;
|
||||
_curve.Height = 120.0f;
|
||||
_curve.Edited += OnCurveEdited;
|
||||
_firstTimeShow = 4; // For some weird reason it needs several frames of warmup (probably due to sliders smoothing)
|
||||
_splitter = new Splitter
|
||||
@@ -188,10 +164,6 @@ namespace FlaxEditor.CustomEditors.Dedicated
|
||||
private void OnSplitterMoved(Float2 location)
|
||||
{
|
||||
_curve.Height = Mathf.Clamp(_splitter.PointToParent(location).Y, 50.0f, 1000.0f);
|
||||
|
||||
// Cache curve height
|
||||
if (_heightCachedPath != null)
|
||||
Editor.Instance.ProjectCache.SetCustomData(_heightCachedPath, _curve.Height);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
|
||||
@@ -1057,7 +1057,6 @@ namespace FlaxEditor.CustomEditors.Dedicated
|
||||
protected override void Deinitialize()
|
||||
{
|
||||
_scriptToggles = null;
|
||||
_scripts.Clear();
|
||||
|
||||
base.Deinitialize();
|
||||
}
|
||||
|
||||
@@ -123,9 +123,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
{
|
||||
base.Refresh();
|
||||
|
||||
var differentValues = HasDifferentValues;
|
||||
Picker.DifferentValues = differentValues;
|
||||
if (!differentValues)
|
||||
if (!HasDifferentValues)
|
||||
{
|
||||
_isRefreshing = true;
|
||||
var value = Values[0];
|
||||
@@ -377,9 +375,12 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
{
|
||||
base.Refresh();
|
||||
|
||||
_isRefreshing = true;
|
||||
_textBox.Text = HasDifferentValues ? "Multiple Values" : GetPath();
|
||||
_isRefreshing = false;
|
||||
if (!HasDifferentValues)
|
||||
{
|
||||
_isRefreshing = true;
|
||||
_textBox.Text = GetPath();
|
||||
_isRefreshing = false;
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
|
||||
@@ -26,8 +26,6 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
public override void Initialize(LayoutElementsContainer layout)
|
||||
{
|
||||
_label = layout.ClickableLabel(Path).CustomControl;
|
||||
_label.Margin = new Margin(0, 20.0f, 0, 0);
|
||||
_label.ClipText = true;
|
||||
_label.RightClick += ShowPicker;
|
||||
var button = new Button
|
||||
{
|
||||
|
||||
@@ -9,8 +9,6 @@ using FlaxEditor.GUI.Drag;
|
||||
using FlaxEditor.SceneGraph;
|
||||
using FlaxEditor.SceneGraph.GUI;
|
||||
using FlaxEditor.Scripting;
|
||||
using FlaxEditor.Windows;
|
||||
using FlaxEditor.Windows.Assets;
|
||||
using FlaxEngine;
|
||||
using FlaxEngine.GUI;
|
||||
using FlaxEngine.Utilities;
|
||||
@@ -42,11 +40,6 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
private DragScripts _dragScripts;
|
||||
private DragHandlers _dragHandlers;
|
||||
|
||||
/// <summary>
|
||||
/// The presenter using this control.
|
||||
/// </summary>
|
||||
public IPresenterOwner PresenterContext;
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the allowed objects type (given type and all sub classes). Must be <see cref="Object"/> type of any subclass.
|
||||
/// </summary>
|
||||
@@ -136,11 +129,6 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
/// </summary>
|
||||
public Func<Object, ScriptType, bool> CheckValid;
|
||||
|
||||
/// <summary>
|
||||
/// Utility flag used to indicate that there are different values assigned to this reference editor and user should be informed about it.
|
||||
/// </summary>
|
||||
public bool DifferentValues;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="FlaxObjectRefPickerControl"/> class.
|
||||
/// </summary>
|
||||
@@ -166,7 +154,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
Value = actor;
|
||||
RootWindow.Focus();
|
||||
Focus();
|
||||
}, PresenterContext);
|
||||
});
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -175,7 +163,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
Value = script;
|
||||
RootWindow.Focus();
|
||||
Focus();
|
||||
}, PresenterContext);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -209,14 +197,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
Render2D.DrawRectangle(frameRect, isEnabled && (IsMouseOver || IsNavFocused) ? style.BorderHighlighted : style.BorderNormal);
|
||||
|
||||
// Check if has item selected
|
||||
if (DifferentValues)
|
||||
{
|
||||
// Draw info
|
||||
Render2D.PushClip(nameRect);
|
||||
Render2D.DrawText(style.FontMedium, Type != null ? $"Multiple Values ({Utilities.Utils.GetPropertyNameUI(Type.ToString())})" : "-", nameRect, isEnabled ? style.ForegroundGrey : style.ForegroundGrey.AlphaMultiplied(0.75f), TextAlignment.Near, TextAlignment.Center);
|
||||
Render2D.PopClip();
|
||||
}
|
||||
else if (isSelected)
|
||||
if (isSelected)
|
||||
{
|
||||
// Draw name
|
||||
Render2D.PushClip(nameRect);
|
||||
@@ -345,19 +326,10 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
}
|
||||
else
|
||||
{
|
||||
if (PresenterContext is PropertiesWindow)
|
||||
_linkedTreeNode = Editor.Instance.Scene.GetActorNode(actor).TreeNode;
|
||||
else if (PresenterContext is PrefabWindow prefabWindow)
|
||||
_linkedTreeNode = prefabWindow.Graph.Root.Find(actor).TreeNode;
|
||||
if (_linkedTreeNode != null)
|
||||
{
|
||||
_linkedTreeNode.ExpandAllParents();
|
||||
if (PresenterContext is PropertiesWindow)
|
||||
Editor.Instance.Windows.SceneWin.SceneTreePanel.ScrollViewTo(_linkedTreeNode, true);
|
||||
else if (PresenterContext is PrefabWindow prefabWindow)
|
||||
(prefabWindow.Tree.Parent as Panel).ScrollViewTo(_linkedTreeNode, true);
|
||||
_linkedTreeNode.StartHighlight();
|
||||
}
|
||||
_linkedTreeNode = Editor.Instance.Scene.GetActorNode(actor).TreeNode;
|
||||
_linkedTreeNode.ExpandAllParents();
|
||||
Editor.Instance.Windows.SceneWin.SceneTreePanel.ScrollViewTo(_linkedTreeNode, true);
|
||||
_linkedTreeNode.StartHighlight();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -400,20 +372,9 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
|
||||
// Select object
|
||||
if (_value is Actor actor)
|
||||
{
|
||||
if (PresenterContext is PropertiesWindow)
|
||||
Editor.Instance.SceneEditing.Select(actor);
|
||||
else if (PresenterContext is PrefabWindow prefabWindow)
|
||||
prefabWindow.Select(prefabWindow.Graph.Root.Find(actor));
|
||||
}
|
||||
Editor.Instance.SceneEditing.Select(actor);
|
||||
else if (_value is Script script && script.Actor)
|
||||
{
|
||||
var a = script.Actor;
|
||||
if (PresenterContext is PropertiesWindow)
|
||||
Editor.Instance.SceneEditing.Select(a);
|
||||
else if (PresenterContext is PrefabWindow prefabWindow)
|
||||
prefabWindow.Select(prefabWindow.Graph.Root.Find(a));
|
||||
}
|
||||
Editor.Instance.SceneEditing.Select(script.Actor);
|
||||
else if (_value is Asset asset)
|
||||
Editor.Instance.Windows.ContentWin.Select(asset);
|
||||
}
|
||||
@@ -454,13 +415,13 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
|
||||
// Ensure to have valid drag helpers (uses lazy init)
|
||||
if (_dragActors == null)
|
||||
_dragActors = new DragActors(ValidateDragActor);
|
||||
_dragActors = new DragActors(x => IsValid(x.Actor));
|
||||
if (_dragActorsWithScript == null)
|
||||
_dragActorsWithScript = new DragActors(ValidateDragActorWithScript);
|
||||
if (_dragAssets == null)
|
||||
_dragAssets = new DragAssets(ValidateDragAsset);
|
||||
if (_dragScripts == null)
|
||||
_dragScripts = new DragScripts(ValidateDragScript);
|
||||
_dragScripts = new DragScripts(IsValid);
|
||||
if (_dragHandlers == null)
|
||||
{
|
||||
_dragHandlers = new DragHandlers
|
||||
@@ -485,43 +446,6 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
return DragEffect;
|
||||
}
|
||||
|
||||
private bool ValidateDragActor(ActorNode a)
|
||||
{
|
||||
if (!IsValid(a.Actor))
|
||||
return false;
|
||||
|
||||
if (PresenterContext is PrefabWindow prefabWindow)
|
||||
{
|
||||
if (prefabWindow.Tree == a.TreeNode.ParentTree)
|
||||
return true;
|
||||
}
|
||||
else if (PresenterContext is PropertiesWindow || PresenterContext == null)
|
||||
{
|
||||
if (a.ParentScene != null)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private bool ValidateDragScript(Script script)
|
||||
{
|
||||
if (!IsValid(script))
|
||||
return false;
|
||||
|
||||
if (PresenterContext is PrefabWindow prefabWindow)
|
||||
{
|
||||
var actorNode = prefabWindow.Graph.Root.Find(script.Actor);
|
||||
if (actorNode != null)
|
||||
return true;
|
||||
}
|
||||
else if (PresenterContext is PropertiesWindow || PresenterContext == null)
|
||||
{
|
||||
if (script.Actor.HasScene)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private bool ValidateDragAsset(AssetItem assetItem)
|
||||
{
|
||||
// Check if can accept assets
|
||||
@@ -540,18 +464,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
|
||||
private bool ValidateDragActorWithScript(ActorNode node)
|
||||
{
|
||||
bool isCorrectContext = false;
|
||||
if (PresenterContext is PrefabWindow prefabWindow)
|
||||
{
|
||||
if (prefabWindow.Tree == node.TreeNode.ParentTree)
|
||||
isCorrectContext = true;
|
||||
}
|
||||
else if (PresenterContext is PropertiesWindow || PresenterContext == null)
|
||||
{
|
||||
if (node.ParentScene != null)
|
||||
isCorrectContext = true;
|
||||
}
|
||||
return node.Actor.Scripts.Any(IsValid) && isCorrectContext;
|
||||
return node.Actor.Scripts.Any(IsValid);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
@@ -623,7 +536,6 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
if (!HasDifferentTypes)
|
||||
{
|
||||
_element = layout.Custom<FlaxObjectRefPickerControl>();
|
||||
_element.CustomControl.PresenterContext = Presenter.Owner;
|
||||
_element.CustomControl.Type = Values.Type.Type != typeof(object) || Values[0] == null ? Values.Type : TypeUtils.GetObjectType(Values[0]);
|
||||
_element.CustomControl.ValueChanged += () => SetValue(_element.CustomControl.Value);
|
||||
}
|
||||
@@ -634,9 +546,7 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
{
|
||||
base.Refresh();
|
||||
|
||||
var differentValues = HasDifferentValues;
|
||||
_element.CustomControl.DifferentValues = differentValues;
|
||||
if (!differentValues)
|
||||
if (!HasDifferentValues)
|
||||
{
|
||||
_element.CustomControl.Value = Values[0] as Object;
|
||||
}
|
||||
|
||||
@@ -819,15 +819,6 @@ namespace FlaxEditor.CustomEditors.Editors
|
||||
OnGroupsEnd();
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void Deinitialize()
|
||||
{
|
||||
_visibleIfCaches = null;
|
||||
_visibleIfPropertiesListsCache = null;
|
||||
|
||||
base.Deinitialize();
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void Refresh()
|
||||
{
|
||||
|
||||
@@ -96,20 +96,6 @@ namespace FlaxEditor.CustomEditors
|
||||
menu.Show(groupPanel, location);
|
||||
}
|
||||
|
||||
internal string GetLayoutCachePath(string name)
|
||||
{
|
||||
// Build group identifier (made of path from group titles)
|
||||
var expandPath = name;
|
||||
var container = this;
|
||||
while (container != null && !(container is CustomEditorPresenter))
|
||||
{
|
||||
if (container.ContainerControl is DropPanel dropPanel)
|
||||
expandPath = dropPanel.HeaderText + "/" + expandPath;
|
||||
container = container._parent;
|
||||
}
|
||||
return expandPath;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Adds new group element.
|
||||
/// </summary>
|
||||
@@ -126,7 +112,14 @@ namespace FlaxEditor.CustomEditors
|
||||
if (presenter != null && (presenter.Features & FeatureFlags.CacheExpandedGroups) != 0)
|
||||
{
|
||||
// Build group identifier (made of path from group titles)
|
||||
var expandPath = GetLayoutCachePath(title);
|
||||
var expandPath = title;
|
||||
var container = this;
|
||||
while (container != null && !(container is CustomEditorPresenter))
|
||||
{
|
||||
if (container.ContainerControl is DropPanel dropPanel)
|
||||
expandPath = dropPanel.HeaderText + "/" + expandPath;
|
||||
container = container._parent;
|
||||
}
|
||||
|
||||
// Caching/restoring expanded groups (non-root groups cache expanded state so invert boolean expression)
|
||||
if (Editor.Instance.ProjectCache.IsGroupToggled(expandPath) ^ isSubGroup)
|
||||
|
||||
@@ -250,7 +250,7 @@ namespace FlaxEditor.CustomEditors
|
||||
if (objA == null && objB is string objBStr && objBStr.Length == 0)
|
||||
return true;
|
||||
|
||||
return FlaxEngine.Json.JsonSerializer.ValueEquals(objA, objB);
|
||||
return Newtonsoft.Json.Utilities.MiscellaneousUtils.ValueEquals(objA, objB);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -1686,6 +1686,9 @@ namespace FlaxEditor
|
||||
[return: MarshalAs(UnmanagedType.U1)]
|
||||
internal static partial bool Internal_CanSetToRoot(IntPtr prefab, IntPtr newRoot);
|
||||
|
||||
[LibraryImport("FlaxEngine", EntryPoint = "EditorInternal_GetPrefabNestedObject", StringMarshalling = StringMarshalling.Custom, StringMarshallingCustomType = typeof(StringMarshaller))]
|
||||
internal static partial void Internal_GetPrefabNestedObject(IntPtr prefabId, IntPtr prefabObjectId, IntPtr outPrefabId, IntPtr outPrefabObjectId);
|
||||
|
||||
[LibraryImport("FlaxEngine", EntryPoint = "EditorInternal_GetAnimationTime", StringMarshalling = StringMarshalling.Custom, StringMarshallingCustomType = typeof(StringMarshaller))]
|
||||
internal static partial float Internal_GetAnimationTime(IntPtr animatedModel);
|
||||
|
||||
|
||||
@@ -48,11 +48,6 @@ namespace FlaxEditor.GUI
|
||||
/// </summary>
|
||||
public bool CanEdit = true;
|
||||
|
||||
/// <summary>
|
||||
/// Utility flag used to indicate that there are different values assigned to this reference editor and user should be informed about it.
|
||||
/// </summary>
|
||||
public bool DifferentValues;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="AssetPicker"/> class.
|
||||
/// </summary>
|
||||
@@ -126,13 +121,7 @@ namespace FlaxEditor.GUI
|
||||
if (CanEdit)
|
||||
Render2D.DrawSprite(style.ArrowDown, button1Rect, button1Rect.Contains(_mousePos) ? style.Foreground : style.ForegroundGrey);
|
||||
|
||||
if (DifferentValues)
|
||||
{
|
||||
// No element selected
|
||||
Render2D.FillRectangle(iconRect, style.BackgroundNormal);
|
||||
Render2D.DrawText(style.FontMedium, "Multiple\nValues", iconRect, style.Foreground, TextAlignment.Center, TextAlignment.Center, TextWrapping.NoWrap, 1.0f, Height / DefaultIconSize);
|
||||
}
|
||||
else if (Validator.SelectedItem != null)
|
||||
if (Validator.SelectedItem != null)
|
||||
{
|
||||
// Draw item preview
|
||||
Validator.SelectedItem.DrawThumbnail(ref iconRect);
|
||||
|
||||
@@ -30,10 +30,8 @@ namespace FlaxEditor.GUI
|
||||
internal bool _isMovingTangent;
|
||||
internal bool _movedView;
|
||||
internal bool _movedKeyframes;
|
||||
internal bool _toggledSelection;
|
||||
private TangentPoint _movingTangent;
|
||||
private Float2 _movingSelectionStart;
|
||||
private Float2 _movingSelectionStartPosLock;
|
||||
private Float2[] _movingSelectionOffsets;
|
||||
private Float2 _cmShowPos;
|
||||
|
||||
@@ -58,11 +56,12 @@ namespace FlaxEditor.GUI
|
||||
internal void UpdateSelection(ref Rectangle selectionRect)
|
||||
{
|
||||
// Find controls to select
|
||||
var children = _children;
|
||||
for (int i = 0; i < children.Count; i++)
|
||||
for (int i = 0; i < Children.Count; i++)
|
||||
{
|
||||
if (children[i] is KeyframePoint p)
|
||||
if (Children[i] is KeyframePoint p)
|
||||
{
|
||||
p.IsSelected = p.Bounds.Intersects(ref selectionRect);
|
||||
}
|
||||
}
|
||||
_editor.UpdateTangents();
|
||||
}
|
||||
@@ -73,7 +72,6 @@ namespace FlaxEditor.GUI
|
||||
_isMovingSelection = true;
|
||||
_movedKeyframes = false;
|
||||
var viewRect = _editor._mainPanel.GetClientArea();
|
||||
_movingSelectionStartPosLock = location;
|
||||
_movingSelectionStart = PointToKeyframes(location, ref viewRect);
|
||||
if (_movingSelectionOffsets == null || _movingSelectionOffsets.Length != _editor._points.Count)
|
||||
_movingSelectionOffsets = new Float2[_editor._points.Count];
|
||||
@@ -84,17 +82,10 @@ namespace FlaxEditor.GUI
|
||||
|
||||
internal void OnMove(Float2 location)
|
||||
{
|
||||
// Skip updating keyframes until move actual starts to be meaningful
|
||||
if (Float2.Distance(ref _movingSelectionStartPosLock, ref location) < 1.5f)
|
||||
return;
|
||||
_movingSelectionStartPosLock = Float2.Minimum;
|
||||
|
||||
var viewRect = _editor._mainPanel.GetClientArea();
|
||||
var locationKeyframes = PointToKeyframes(location, ref viewRect);
|
||||
var accessor = _editor.Accessor;
|
||||
var components = accessor.GetCurveComponents();
|
||||
var snapEnabled = Root.GetKey(KeyboardKeys.Control);
|
||||
var snapGrid = snapEnabled ? _editor.GetGridSnap() : Float2.One;
|
||||
for (var i = 0; i < _editor._points.Count; i++)
|
||||
{
|
||||
var p = _editor._points[i];
|
||||
@@ -131,20 +122,7 @@ namespace FlaxEditor.GUI
|
||||
if (isFirstSelected)
|
||||
{
|
||||
time = locationKeyframes.X + offset.X;
|
||||
}
|
||||
|
||||
if (snapEnabled)
|
||||
{
|
||||
// Snap to the grid
|
||||
var key = new Float2(time, value);
|
||||
key = Float2.SnapToGrid(key, snapGrid);
|
||||
time = key.X;
|
||||
value = key.Y;
|
||||
}
|
||||
|
||||
// Clamp and snap time to the valid range
|
||||
if (isFirstSelected)
|
||||
{
|
||||
if (_editor.FPS.HasValue)
|
||||
{
|
||||
float fps = _editor.FPS.Value;
|
||||
@@ -153,6 +131,8 @@ namespace FlaxEditor.GUI
|
||||
time = Mathf.Clamp(time, minTime, maxTime);
|
||||
}
|
||||
|
||||
// TODO: snapping keyframes to grid when moving
|
||||
|
||||
_editor.SetKeyframeInternal(p.Index, time, value, p.Component);
|
||||
}
|
||||
_editor.UpdateKeyframes();
|
||||
@@ -254,11 +234,7 @@ namespace FlaxEditor.GUI
|
||||
var k = _editor.GetKeyframe(_movingTangent.Index);
|
||||
var kv = _editor.GetKeyframeValue(k);
|
||||
var value = _editor.Accessor.GetCurveValue(ref kv, _movingTangent.Component);
|
||||
var tangent = PointToKeyframes(location, ref viewRect).Y - value;
|
||||
if (Root.GetKey(KeyboardKeys.Control))
|
||||
tangent = Float2.SnapToGrid(new Float2(0, tangent), _editor.GetGridSnap()).Y; // Snap tangent over Y axis
|
||||
tangent = tangent * _editor.ViewScale.X * 2;
|
||||
_movingTangent.TangentValue = tangent;
|
||||
_movingTangent.TangentValue = PointToKeyframes(location, ref viewRect).Y - value;
|
||||
_editor.UpdateTangents();
|
||||
Cursor = CursorType.SizeNS;
|
||||
_movedKeyframes = true;
|
||||
@@ -307,7 +283,6 @@ namespace FlaxEditor.GUI
|
||||
}
|
||||
|
||||
// Cache data
|
||||
_toggledSelection = false;
|
||||
_isMovingSelection = false;
|
||||
_isMovingTangent = false;
|
||||
_mousePos = location;
|
||||
@@ -330,7 +305,13 @@ namespace FlaxEditor.GUI
|
||||
{
|
||||
if (_leftMouseDown)
|
||||
{
|
||||
if (Root.GetKey(KeyboardKeys.Shift))
|
||||
if (Root.GetKey(KeyboardKeys.Control))
|
||||
{
|
||||
// Toggle selection
|
||||
keyframe.IsSelected = !keyframe.IsSelected;
|
||||
_editor.UpdateTangents();
|
||||
}
|
||||
else if (Root.GetKey(KeyboardKeys.Shift))
|
||||
{
|
||||
// Select range
|
||||
keyframe.IsSelected = true;
|
||||
@@ -354,14 +335,10 @@ namespace FlaxEditor.GUI
|
||||
else if (!keyframe.IsSelected)
|
||||
{
|
||||
// Select node
|
||||
if (!Root.GetKey(KeyboardKeys.Control))
|
||||
{
|
||||
if (_editor.KeyframesEditorContext != null)
|
||||
_editor.KeyframesEditorContext.OnKeyframesDeselect(_editor);
|
||||
else
|
||||
_editor.ClearSelection();
|
||||
}
|
||||
_toggledSelection = true;
|
||||
if (_editor.KeyframesEditorContext != null)
|
||||
_editor.KeyframesEditorContext.OnKeyframesDeselect(_editor);
|
||||
else
|
||||
_editor.ClearSelection();
|
||||
keyframe.IsSelected = true;
|
||||
_editor.UpdateTangents();
|
||||
}
|
||||
@@ -452,12 +429,6 @@ namespace FlaxEditor.GUI
|
||||
else
|
||||
OnMoveEnd(location);
|
||||
}
|
||||
// Toggle selection
|
||||
else if (!_toggledSelection && Root.GetKey(KeyboardKeys.Control) && GetChildAt(location) is KeyframePoint keyframe)
|
||||
{
|
||||
keyframe.IsSelected = !keyframe.IsSelected;
|
||||
_editor.UpdateTangents();
|
||||
}
|
||||
|
||||
_isMovingSelection = false;
|
||||
_isMovingTangent = false;
|
||||
@@ -543,11 +514,11 @@ namespace FlaxEditor.GUI
|
||||
{
|
||||
if (base.OnMouseDoubleClick(location, button))
|
||||
return true;
|
||||
|
||||
|
||||
// Add keyframe on double click
|
||||
var child = GetChildAt(location);
|
||||
if (child is not KeyframePoint &&
|
||||
child is not TangentPoint &&
|
||||
if (child is not KeyframePoint &&
|
||||
child is not TangentPoint &&
|
||||
_editor.KeyframesCount < _editor.MaxKeyframes)
|
||||
{
|
||||
var viewRect = _editor._mainPanel.GetClientArea();
|
||||
@@ -574,7 +545,7 @@ namespace FlaxEditor.GUI
|
||||
var viewRect = _editor._mainPanel.GetClientArea();
|
||||
var locationInKeyframes = PointToKeyframes(location, ref viewRect);
|
||||
var locationInEditorBefore = _editor.PointFromKeyframes(locationInKeyframes, ref viewRect);
|
||||
|
||||
|
||||
// Scale relative to the curve size
|
||||
var scale = new Float2(delta * 0.1f);
|
||||
_editor._mainPanel.GetDesireClientArea(out var mainPanelArea);
|
||||
|
||||
@@ -163,11 +163,10 @@ namespace FlaxEditor.GUI
|
||||
/// <inheritdoc />
|
||||
public override void Draw()
|
||||
{
|
||||
var style = Style.Current;
|
||||
var rect = new Rectangle(Float2.Zero, Size);
|
||||
var color = Editor.ShowCollapsed ? style.ForegroundDisabled : Editor.Colors[Component];
|
||||
var color = Editor.ShowCollapsed ? Color.Gray : Editor.Colors[Component];
|
||||
if (IsSelected)
|
||||
color = Editor.ContainsFocus ? style.SelectionBorder : Color.Lerp(style.ForegroundDisabled, style.SelectionBorder, 0.4f);
|
||||
color = Editor.ContainsFocus ? Color.YellowGreen : Color.Lerp(Color.Gray, Color.YellowGreen, 0.4f);
|
||||
if (IsMouseOver)
|
||||
color *= 1.1f;
|
||||
Render2D.FillRectangle(rect, color);
|
||||
@@ -245,19 +244,14 @@ namespace FlaxEditor.GUI
|
||||
set => Editor.SetKeyframeTangentInternal(Index, IsIn, Component, value);
|
||||
}
|
||||
|
||||
internal float TangentOffset => 50.0f / Editor.ViewScale.X;
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void Draw()
|
||||
{
|
||||
var style = Style.Current;
|
||||
var thickness = 6.0f / Mathf.Max(Editor.ViewScale.X, 1.0f);
|
||||
var size = Size;
|
||||
var pointPos = PointFromParent(Point.Center);
|
||||
Render2D.DrawLine(size * 0.5f, pointPos, style.ForegroundDisabled, thickness);
|
||||
Render2D.DrawLine(Size * 0.5f, pointPos, Color.Gray);
|
||||
|
||||
var rect = new Rectangle(Float2.Zero, size);
|
||||
var color = style.BorderSelected;
|
||||
var rect = new Rectangle(Float2.Zero, Size);
|
||||
var color = Color.MediumVioletRed;
|
||||
if (IsMouseOver)
|
||||
color *= 1.1f;
|
||||
Render2D.FillRectangle(rect, color);
|
||||
@@ -295,7 +289,7 @@ namespace FlaxEditor.GUI
|
||||
/// <summary>
|
||||
/// The curve time/value axes tick steps.
|
||||
/// </summary>
|
||||
protected double[] TickSteps = Utilities.Utils.CurveTickSteps;
|
||||
protected float[] TickSteps = Utilities.Utils.CurveTickSteps;
|
||||
|
||||
/// <summary>
|
||||
/// The curve contents area.
|
||||
@@ -448,7 +442,7 @@ namespace FlaxEditor.GUI
|
||||
_mainPanel = new Panel(ScrollBars.Both)
|
||||
{
|
||||
ScrollMargin = new Margin(150.0f),
|
||||
AlwaysShowScrollbars = false,
|
||||
AlwaysShowScrollbars = true,
|
||||
AnchorPreset = AnchorPresets.StretchAll,
|
||||
Offsets = Margin.Zero,
|
||||
Parent = this
|
||||
@@ -674,82 +668,26 @@ namespace FlaxEditor.GUI
|
||||
OnEditingEnd();
|
||||
}
|
||||
|
||||
private void ShowCurve(bool selectedOnly)
|
||||
{
|
||||
if (_points.Count == 0)
|
||||
return;
|
||||
int pass = 1;
|
||||
REDO:
|
||||
|
||||
// Get curve bounds in Keyframes (time and value)
|
||||
Float2 posMin = Float2.Maximum, posMax = Float2.Minimum;
|
||||
// TODO: include bezier curve bounds calculation to handle curve outside the bounds made out of points
|
||||
foreach (var point in _points)
|
||||
{
|
||||
if (selectedOnly && !point.IsSelected)
|
||||
continue;
|
||||
var pos = point.Point;
|
||||
Float2.Min(ref posMin, ref pos, out posMin);
|
||||
Float2.Max(ref posMax, ref pos, out posMax);
|
||||
}
|
||||
|
||||
// Apply margin around the area
|
||||
var posMargin = (posMax - posMin) * 0.05f;
|
||||
posMin -= posMargin;
|
||||
posMax += posMargin;
|
||||
|
||||
// Convert from Keyframes to Contents
|
||||
_mainPanel.GetDesireClientArea(out var viewRect);
|
||||
PointFromKeyframesToContents(ref posMin, ref viewRect);
|
||||
PointFromKeyframesToContents(ref posMax, ref viewRect);
|
||||
var tmp = posMin;
|
||||
Float2.Min(ref posMin, ref posMax, out posMin);
|
||||
Float2.Max(ref posMax, ref tmp, out posMax);
|
||||
var contentsSize = posMax - posMin;
|
||||
|
||||
// Convert from Contents to Main Panel
|
||||
posMin = _contents.PointToParent(posMin);
|
||||
posMax = _contents.PointToParent(posMax);
|
||||
tmp = posMin;
|
||||
Float2.Min(ref posMin, ref posMax, out posMin);
|
||||
Float2.Max(ref posMax, ref tmp, out posMax);
|
||||
|
||||
// Update zoom (leave unchanged when focusing a single point)
|
||||
var zoomMask = EnableZoom;
|
||||
if (Mathf.IsZero(posMargin.X))
|
||||
zoomMask &= ~UseMode.Horizontal;
|
||||
if (Mathf.IsZero(posMargin.Y))
|
||||
zoomMask &= ~UseMode.Vertical;
|
||||
ViewScale = ApplyUseModeMask(zoomMask, viewRect.Size / contentsSize, ViewScale);
|
||||
|
||||
// Update scroll (attempt to center the area when it's smaller than the view)
|
||||
Float2 viewOffset = -posMin;
|
||||
Float2 viewSize = _mainPanel.Size;
|
||||
Float2 viewSizeLeft = viewSize - Float2.Clamp(posMax - posMin, Float2.Zero, viewSize);
|
||||
viewOffset += viewSizeLeft * 0.5f;
|
||||
viewOffset = ApplyUseModeMask(EnablePanning, viewOffset, _mainPanel.ViewOffset);
|
||||
_mainPanel.ViewOffset = viewOffset;
|
||||
|
||||
// Do it multiple times so the view offset can be properly calculate once the view scale gets changes
|
||||
if (pass++ <= 2)
|
||||
goto REDO;
|
||||
|
||||
UpdateKeyframes();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Focuses the view on the selected keyframes.
|
||||
/// </summary>
|
||||
public void FocusSelection()
|
||||
{
|
||||
// Fallback to showing whole curve if nothing is selected
|
||||
ShowCurve(SelectionCount != 0);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void ShowWholeCurve()
|
||||
{
|
||||
ShowCurve(false);
|
||||
_mainPanel.GetDesireClientArea(out var mainPanelArea);
|
||||
ViewScale = ApplyUseModeMask(EnableZoom, mainPanelArea.Size / _contents.Size, ViewScale);
|
||||
Float2 minPos = Float2.Maximum;
|
||||
foreach (var point in _points)
|
||||
{
|
||||
var pos = point.PointToParent(point.Location);
|
||||
Float2.Min(ref minPos, ref pos, out minPos);
|
||||
}
|
||||
var minPosPoint = _contents.PointToParent(ref minPos);
|
||||
var scroll = new Float2(_mainPanel.HScrollBar?.TargetValue ?? 0, _mainPanel.VScrollBar?.TargetValue ?? 0);
|
||||
scroll = ApplyUseModeMask(EnablePanning, minPosPoint, scroll);
|
||||
if (_mainPanel.HScrollBar != null)
|
||||
_mainPanel.HScrollBar.TargetValue = scroll.X;
|
||||
if (_mainPanel.VScrollBar != null)
|
||||
_mainPanel.VScrollBar.TargetValue = scroll.Y;
|
||||
|
||||
UpdateKeyframes();
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
@@ -828,7 +766,10 @@ namespace FlaxEditor.GUI
|
||||
point = _contents.PointFromParent(point);
|
||||
|
||||
// Contents -> Keyframes
|
||||
return PointFromContentsToKeyframes(ref point, ref curveContentAreaBounds);
|
||||
return new Float2(
|
||||
(point.X + _contents.Location.X) / UnitsPerSecond,
|
||||
(point.Y + _contents.Location.Y - curveContentAreaBounds.Height) / -UnitsPerSecond
|
||||
);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -840,7 +781,10 @@ namespace FlaxEditor.GUI
|
||||
protected Float2 PointFromKeyframes(Float2 point, ref Rectangle curveContentAreaBounds)
|
||||
{
|
||||
// Keyframes -> Contents
|
||||
PointFromKeyframesToContents(ref point, ref curveContentAreaBounds);
|
||||
point = new Float2(
|
||||
point.X * UnitsPerSecond - _contents.Location.X,
|
||||
point.Y * -UnitsPerSecond + curveContentAreaBounds.Height - _contents.Location.Y
|
||||
);
|
||||
|
||||
// Contents -> Main Panel
|
||||
point = _contents.PointToParent(point);
|
||||
@@ -849,27 +793,11 @@ namespace FlaxEditor.GUI
|
||||
return _mainPanel.PointToParent(point);
|
||||
}
|
||||
|
||||
internal Float2 PointFromContentsToKeyframes(ref Float2 point, ref Rectangle curveContentAreaBounds)
|
||||
{
|
||||
return new Float2(
|
||||
(point.X + _contents.Location.X) / UnitsPerSecond,
|
||||
(point.Y + _contents.Location.Y - curveContentAreaBounds.Height) / -UnitsPerSecond
|
||||
);
|
||||
}
|
||||
|
||||
internal void PointFromKeyframesToContents(ref Float2 point, ref Rectangle curveContentAreaBounds)
|
||||
{
|
||||
point = new Float2(
|
||||
point.X * UnitsPerSecond - _contents.Location.X,
|
||||
point.Y * -UnitsPerSecond + curveContentAreaBounds.Height - _contents.Location.Y
|
||||
);
|
||||
}
|
||||
|
||||
private void DrawAxis(Float2 axis, Rectangle viewRect, float min, float max, float pixelRange)
|
||||
{
|
||||
Utilities.Utils.DrawCurveTicks((decimal tick, double step, float strength) =>
|
||||
Utilities.Utils.DrawCurveTicks((float tick, float strength) =>
|
||||
{
|
||||
var p = PointFromKeyframes(axis * (float)tick, ref viewRect);
|
||||
var p = PointFromKeyframes(axis * tick, ref viewRect);
|
||||
|
||||
// Draw line
|
||||
var lineRect = new Rectangle
|
||||
@@ -892,24 +820,6 @@ namespace FlaxEditor.GUI
|
||||
}, TickSteps, ref _tickStrengths, min, max, pixelRange);
|
||||
}
|
||||
|
||||
private void SetupGrid(out Float2 min, out Float2 max, out Float2 pixelRange)
|
||||
{
|
||||
var viewRect = _mainPanel.GetClientArea();
|
||||
var upperLeft = PointToKeyframes(viewRect.Location, ref viewRect);
|
||||
var bottomRight = PointToKeyframes(viewRect.Size, ref viewRect);
|
||||
|
||||
min = Float2.Min(upperLeft, bottomRight);
|
||||
max = Float2.Max(upperLeft, bottomRight);
|
||||
pixelRange = (max - min) * ViewScale * UnitsPerSecond;
|
||||
}
|
||||
|
||||
private Float2 GetGridSnap()
|
||||
{
|
||||
SetupGrid(out var min, out var max, out var pixelRange);
|
||||
return new Float2(Utilities.Utils.GetCurveGridSnap(TickSteps, ref _tickStrengths, min.X, max.X, pixelRange.X),
|
||||
Utilities.Utils.GetCurveGridSnap(TickSteps, ref _tickStrengths, min.Y, max.Y, pixelRange.Y));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Draws the curve.
|
||||
/// </summary>
|
||||
@@ -939,7 +849,12 @@ namespace FlaxEditor.GUI
|
||||
// Draw time and values axes
|
||||
if (ShowAxes != UseMode.Off)
|
||||
{
|
||||
SetupGrid(out var min, out var max, out var pixelRange);
|
||||
var upperLeft = PointToKeyframes(viewRect.Location, ref viewRect);
|
||||
var bottomRight = PointToKeyframes(viewRect.Size, ref viewRect);
|
||||
|
||||
var min = Float2.Min(upperLeft, bottomRight);
|
||||
var max = Float2.Max(upperLeft, bottomRight);
|
||||
var pixelRange = (max - min) * ViewScale * UnitsPerSecond;
|
||||
|
||||
Render2D.PushClip(ref viewRect);
|
||||
|
||||
@@ -1024,7 +939,7 @@ namespace FlaxEditor.GUI
|
||||
}
|
||||
else if (options.FocusSelection.Process(this))
|
||||
{
|
||||
FocusSelection();
|
||||
ShowWholeCurve();
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -2285,7 +2200,7 @@ namespace FlaxEditor.GUI
|
||||
|
||||
var tangent = t.TangentValue;
|
||||
var direction = t.IsIn ? -1.0f : 1.0f;
|
||||
var offset = t.TangentOffset;
|
||||
var offset = 30.0f;
|
||||
var location = GetKeyframePoint(ref k, selectedComponent);
|
||||
t.Size = KeyframesSize / ViewScale;
|
||||
t.Location = new Float2
|
||||
@@ -2312,18 +2227,6 @@ namespace FlaxEditor.GUI
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void SetScaleInternal(ref Float2 scale)
|
||||
{
|
||||
base.SetScaleInternal(ref scale);
|
||||
|
||||
if (!_showCollapsed)
|
||||
{
|
||||
// Refresh keyframes when zooming (their size depends on the scale)
|
||||
UpdateKeyframes();
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void OnShowContextMenu(ContextMenu.ContextMenu cm, int selectionCount)
|
||||
{
|
||||
|
||||
@@ -486,7 +486,7 @@ namespace FlaxEditor.GUI.Docking
|
||||
{
|
||||
base.Focus();
|
||||
|
||||
SelectTab(false);
|
||||
SelectTab();
|
||||
BringToFront();
|
||||
}
|
||||
|
||||
|
||||
@@ -1,8 +1,6 @@
|
||||
// Copyright (c) 2012-2024 Wojciech Figat. All rights reserved.
|
||||
|
||||
using System;
|
||||
using FlaxEditor.Windows;
|
||||
using FlaxEditor.Windows.Assets;
|
||||
using FlaxEngine;
|
||||
using FlaxEngine.GUI;
|
||||
|
||||
@@ -57,26 +55,18 @@ namespace FlaxEditor.GUI
|
||||
private IsValidDelegate _isValid;
|
||||
private Action<Actor> _selected;
|
||||
|
||||
private ActorSearchPopup(IsValidDelegate isValid, Action<Actor> selected, CustomEditors.IPresenterOwner context)
|
||||
private ActorSearchPopup(IsValidDelegate isValid, Action<Actor> selected)
|
||||
{
|
||||
_isValid = isValid;
|
||||
_selected = selected;
|
||||
|
||||
ItemClicked += OnItemClicked;
|
||||
|
||||
if (context is PropertiesWindow propertiesWindow || context == null)
|
||||
// TODO: use async thread to search scenes
|
||||
for (int i = 0; i < Level.ScenesCount; i++)
|
||||
{
|
||||
// TODO: use async thread to search scenes
|
||||
for (int i = 0; i < Level.ScenesCount; i++)
|
||||
{
|
||||
Find(Level.GetScene(i));
|
||||
}
|
||||
Find(Level.GetScene(i));
|
||||
}
|
||||
else if (context is PrefabWindow prefabWindow)
|
||||
{
|
||||
Find(prefabWindow.Graph.MainActor);
|
||||
}
|
||||
|
||||
SortItems();
|
||||
}
|
||||
|
||||
@@ -108,11 +98,10 @@ namespace FlaxEditor.GUI
|
||||
/// <param name="showTargetLocation">The show target location.</param>
|
||||
/// <param name="isValid">Event called to check if a given actor item is valid to be used.</param>
|
||||
/// <param name="selected">Event called on actor item pick.</param>
|
||||
/// <param name="context">The presenter owner context (i.e. PrefabWindow, PropertiesWindow).</param>
|
||||
/// <returns>The dialog.</returns>
|
||||
public static ActorSearchPopup Show(Control showTarget, Float2 showTargetLocation, IsValidDelegate isValid, Action<Actor> selected, CustomEditors.IPresenterOwner context)
|
||||
public static ActorSearchPopup Show(Control showTarget, Float2 showTargetLocation, IsValidDelegate isValid, Action<Actor> selected)
|
||||
{
|
||||
var popup = new ActorSearchPopup(isValid, selected, context);
|
||||
var popup = new ActorSearchPopup(isValid, selected);
|
||||
popup.Show(showTarget, showTargetLocation);
|
||||
return popup;
|
||||
}
|
||||
|
||||
@@ -1,8 +1,6 @@
|
||||
// Copyright (c) 2012-2024 Wojciech Figat. All rights reserved.
|
||||
|
||||
using System;
|
||||
using FlaxEditor.Windows;
|
||||
using FlaxEditor.Windows.Assets;
|
||||
using FlaxEngine;
|
||||
using FlaxEngine.GUI;
|
||||
using FlaxEngine.Utilities;
|
||||
@@ -68,26 +66,18 @@ namespace FlaxEditor.GUI
|
||||
private IsValidDelegate _isValid;
|
||||
private Action<Script> _selected;
|
||||
|
||||
private ScriptSearchPopup(IsValidDelegate isValid, Action<Script> selected, CustomEditors.IPresenterOwner context)
|
||||
private ScriptSearchPopup(IsValidDelegate isValid, Action<Script> selected)
|
||||
{
|
||||
_isValid = isValid;
|
||||
_selected = selected;
|
||||
|
||||
ItemClicked += OnItemClicked;
|
||||
|
||||
if (context is PropertiesWindow propertiesWindow || context == null)
|
||||
// TODO: use async thread to search scenes
|
||||
for (int i = 0; i < Level.ScenesCount; i++)
|
||||
{
|
||||
// TODO: use async thread to search scenes
|
||||
for (int i = 0; i < Level.ScenesCount; i++)
|
||||
{
|
||||
Find(Level.GetScene(i));
|
||||
}
|
||||
Find(Level.GetScene(i));
|
||||
}
|
||||
else if (context is PrefabWindow prefabWindow)
|
||||
{
|
||||
Find(prefabWindow.Graph.MainActor);
|
||||
}
|
||||
|
||||
SortItems();
|
||||
}
|
||||
|
||||
@@ -123,11 +113,10 @@ namespace FlaxEditor.GUI
|
||||
/// <param name="showTargetLocation">The show target location.</param>
|
||||
/// <param name="isValid">Event called to check if a given script item is valid to be used.</param>
|
||||
/// <param name="selected">Event called on script item pick.</param>
|
||||
/// <param name="context">The presenter owner context (i.e. PrefabWindow, PropertiesWindow).</param>
|
||||
/// <returns>The dialog.</returns>
|
||||
public static ScriptSearchPopup Show(Control showTarget, Float2 showTargetLocation, IsValidDelegate isValid, Action<Script> selected, CustomEditors.IPresenterOwner context)
|
||||
public static ScriptSearchPopup Show(Control showTarget, Float2 showTargetLocation, IsValidDelegate isValid, Action<Script> selected)
|
||||
{
|
||||
var popup = new ScriptSearchPopup(isValid, selected, context);
|
||||
var popup = new ScriptSearchPopup(isValid, selected);
|
||||
popup.Show(showTarget, showTargetLocation);
|
||||
return popup;
|
||||
}
|
||||
|
||||
@@ -1,13 +1,10 @@
|
||||
// Copyright (c) 2012-2024 Wojciech Figat. All rights reserved.
|
||||
|
||||
using System;
|
||||
using System.ComponentModel;
|
||||
using System.Linq;
|
||||
using FlaxEditor.History;
|
||||
using FlaxEditor.Scripting;
|
||||
using FlaxEngine;
|
||||
using FlaxEngine.GUI;
|
||||
using CategoryAttribute = FlaxEngine.CategoryAttribute;
|
||||
|
||||
namespace FlaxEditor.GUI
|
||||
{
|
||||
@@ -104,26 +101,11 @@ namespace FlaxEditor.GUI
|
||||
if (_isValid(type))
|
||||
{
|
||||
var attributes = type.GetAttributes(true);
|
||||
if (IsHideAttributes(attributes))
|
||||
if (attributes.FirstOrDefault(x => x is HideInEditorAttribute || x is System.Runtime.CompilerServices.CompilerGeneratedAttribute) == null)
|
||||
{
|
||||
var mType = type.Type;
|
||||
if (mType != null)
|
||||
{
|
||||
// Skip if type is compiler-generated
|
||||
if (mType.IsValueType && mType.ReflectedType != null && string.Equals(mType.ReflectedType.Name, "<PrivateImplementationDetails>", StringComparison.Ordinal))
|
||||
continue;
|
||||
|
||||
// Skip if outer type is hidden
|
||||
if (mType.DeclaringType != null && IsHideAttributes(mType.DeclaringType.GetCustomAttributes(true)))
|
||||
continue;
|
||||
|
||||
// Blacklist some types
|
||||
if (typeof(TypeConverter).IsAssignableFrom(mType) ||
|
||||
typeof(IHistoryAction).IsAssignableFrom(mType) ||
|
||||
(mType.Namespace != null && mType.Namespace.StartsWith("Newtonsoft.Json")))
|
||||
continue;
|
||||
}
|
||||
|
||||
if (mType != null && mType.IsValueType && mType.ReflectedType != null && string.Equals(mType.ReflectedType.Name, "<PrivateImplementationDetails>", StringComparison.Ordinal))
|
||||
continue;
|
||||
AddItem(new TypeItemView(type, attributes));
|
||||
}
|
||||
}
|
||||
@@ -131,17 +113,6 @@ namespace FlaxEditor.GUI
|
||||
SortItems();
|
||||
}
|
||||
|
||||
private bool IsHideAttributes(object[] attributes)
|
||||
{
|
||||
return attributes.FirstOrDefault(IsHideAttribute) == null;
|
||||
}
|
||||
|
||||
private bool IsHideAttribute(object attr)
|
||||
{
|
||||
return attr is HideInEditorAttribute ||
|
||||
attr is System.Runtime.CompilerServices.CompilerGeneratedAttribute;
|
||||
}
|
||||
|
||||
private void OnItemClicked(Item item)
|
||||
{
|
||||
_selected(((TypeItemView)item).Type);
|
||||
|
||||
@@ -14,7 +14,7 @@ namespace FlaxEditor.GUI.Timeline.GUI
|
||||
class Background : ContainerControl
|
||||
{
|
||||
private readonly Timeline _timeline;
|
||||
private double[] _tickSteps;
|
||||
private float[] _tickSteps;
|
||||
private float[] _tickStrengths;
|
||||
private bool _isSelecting;
|
||||
private Float2 _selectingStartPos = Float2.Minimum;
|
||||
@@ -176,9 +176,9 @@ namespace FlaxEditor.GUI.Timeline.GUI
|
||||
// Draw vertical lines for time axis
|
||||
var pixelsInRange = _timeline.Zoom;
|
||||
var pixelRange = pixelsInRange * (max - min);
|
||||
var tickRange = Utilities.Utils.DrawCurveTicks((decimal tick, double step, float strength) =>
|
||||
var tickRange = Utilities.Utils.DrawCurveTicks((float tick, float strength) =>
|
||||
{
|
||||
var time = (float)tick / _timeline.FramesPerSecond;
|
||||
var time = tick / _timeline.FramesPerSecond;
|
||||
var x = time * zoom + Timeline.StartOffset;
|
||||
var lineColor = style.ForegroundDisabled.RGBMultiplied(0.7f).AlphaMultiplied(strength);
|
||||
Render2D.FillRectangle(new Rectangle(x - 0.5f, 0, 1.0f, height), lineColor);
|
||||
@@ -233,20 +233,20 @@ namespace FlaxEditor.GUI.Timeline.GUI
|
||||
int l = Mathf.Clamp(smallestTick + level, 0, _tickSteps.Length - 2);
|
||||
var lStep = _tickSteps[l];
|
||||
var lNextStep = _tickSteps[l + 1];
|
||||
var startTick = Mathd.FloorToInt(min / lStep);
|
||||
var endTick = Mathd.CeilToInt(max / lStep);
|
||||
int startTick = Mathf.FloorToInt(min / lStep);
|
||||
int endTick = Mathf.CeilToInt(max / lStep);
|
||||
Color lineColor = style.Foreground.RGBMultiplied(0.8f).AlphaMultiplied(strength);
|
||||
Color labelColor = style.ForegroundDisabled.AlphaMultiplied(strength);
|
||||
for (var i = startTick; i <= endTick; i++)
|
||||
for (int i = startTick; i <= endTick; i++)
|
||||
{
|
||||
if (l < biggestTick && (i % Mathd.RoundToInt(lNextStep / lStep) == 0))
|
||||
if (l < biggestTick && (i % Mathf.RoundToInt(lNextStep / lStep) == 0))
|
||||
continue;
|
||||
var tick = (decimal)lStep * i;
|
||||
var time = (double)tick / _timeline.FramesPerSecond;
|
||||
var x = (float)time * zoom + Timeline.StartOffset;
|
||||
var tick = i * lStep;
|
||||
var time = tick / _timeline.FramesPerSecond;
|
||||
var x = time * zoom + Timeline.StartOffset;
|
||||
|
||||
// Header line
|
||||
var lineRect = new Rectangle((float)x - 0.5f, -verticalLinesHeaderExtend * 0.6f + timeAxisHeaderOffset, 1.0f, verticalLinesHeaderExtend * 0.6f);
|
||||
var lineRect = new Rectangle(x - 0.5f, -verticalLinesHeaderExtend * 0.6f + timeAxisHeaderOffset, 1.0f, verticalLinesHeaderExtend * 0.6f);
|
||||
Render2D.FillRectangle(lineRect, lineColor);
|
||||
|
||||
// Time label
|
||||
|
||||
@@ -8,6 +8,7 @@ using System.Text;
|
||||
using FlaxEditor.CustomEditors;
|
||||
using FlaxEditor.GUI.ContextMenu;
|
||||
using FlaxEditor.Options;
|
||||
using FlaxEditor.Scripting;
|
||||
using FlaxEngine;
|
||||
using FlaxEngine.GUI;
|
||||
using FlaxEngine.Json;
|
||||
|
||||
@@ -264,7 +264,7 @@ namespace FlaxEditor.GUI.Timeline.Tracks
|
||||
|
||||
private void OnClickedSelect()
|
||||
{
|
||||
ActorSearchPopup.Show(this, PointFromScreen(FlaxEngine.Input.MouseScreenPosition), IsActorValid, SetActor, null);
|
||||
ActorSearchPopup.Show(this, PointFromScreen(FlaxEngine.Input.MouseScreenPosition), IsActorValid, SetActor);
|
||||
}
|
||||
|
||||
private void OnClickedSelectActor(Image image, MouseButton button)
|
||||
|
||||
@@ -19,11 +19,12 @@ namespace FlaxEditor.Gizmo
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
private struct Data
|
||||
{
|
||||
public Matrix WorldMatrix;
|
||||
public Matrix ViewProjectionMatrix;
|
||||
public Float4 GridColor;
|
||||
public Float3 ViewPos;
|
||||
public float Far;
|
||||
public Float3 ViewOrigin;
|
||||
public Float3 Padding;
|
||||
public float GridSize;
|
||||
}
|
||||
|
||||
@@ -43,7 +44,6 @@ namespace FlaxEditor.Gizmo
|
||||
{
|
||||
UseSingleTarget = true;
|
||||
Location = PostProcessEffectLocation.Default;
|
||||
Order = -100000; // Draw before any other editor shapes
|
||||
_shader = FlaxEngine.Content.LoadAsyncInternal<Shader>("Shaders/Editor/Grid");
|
||||
}
|
||||
|
||||
@@ -62,6 +62,7 @@ namespace FlaxEditor.Gizmo
|
||||
Profiler.BeginEventGPU("Editor Grid");
|
||||
|
||||
var options = Editor.Instance.Options.Options;
|
||||
Float3 camPos = renderContext.View.WorldPosition;
|
||||
float gridSize = renderContext.View.Far + 20000;
|
||||
|
||||
// Lazy-init resources
|
||||
@@ -96,10 +97,10 @@ namespace FlaxEditor.Gizmo
|
||||
float y = 1.5f; // Add small bias to reduce Z-fighting with geometry at scene origin
|
||||
var vertices = new Float3[]
|
||||
{
|
||||
new Float3(-gridSize, y, -gridSize),
|
||||
new Float3(gridSize, y, gridSize),
|
||||
new Float3(-gridSize, y, gridSize),
|
||||
new Float3(gridSize, y, -gridSize),
|
||||
new Float3(-gridSize + camPos.X, y, -gridSize + camPos.Z),
|
||||
new Float3(gridSize + camPos.X, y, gridSize + camPos.Z),
|
||||
new Float3(-gridSize + camPos.X, y, gridSize + camPos.Z),
|
||||
new Float3(gridSize + camPos.X, y, -gridSize + camPos.Z),
|
||||
};
|
||||
fixed (Float3* ptr = vertices)
|
||||
{
|
||||
@@ -112,12 +113,12 @@ namespace FlaxEditor.Gizmo
|
||||
{
|
||||
var data = new Data();
|
||||
Matrix.Multiply(ref renderContext.View.View, ref renderContext.View.Projection, out var viewProjection);
|
||||
data.WorldMatrix = Matrix.Identity;
|
||||
Matrix.Transpose(ref viewProjection, out data.ViewProjectionMatrix);
|
||||
data.ViewPos = renderContext.View.WorldPosition;
|
||||
data.GridColor = options.Viewport.ViewportGridColor;
|
||||
data.Far = renderContext.View.Far;
|
||||
data.GridSize = options.Viewport.ViewportGridViewDistance;
|
||||
data.ViewOrigin = renderContext.View.Origin;
|
||||
context.UpdateCB(cb, new IntPtr(&data));
|
||||
}
|
||||
|
||||
|
||||
@@ -85,8 +85,6 @@ namespace FlaxEditor.Gizmo
|
||||
/// </summary>
|
||||
public SelectionOutline()
|
||||
{
|
||||
Order = -90000; // Draw before any other editor shapes (except grid gizmo)
|
||||
|
||||
_outlineMaterial = FlaxEngine.Content.LoadAsyncInternal<Material>("Editor/Gizmo/SelectionOutlineMaterial");
|
||||
if (_outlineMaterial)
|
||||
{
|
||||
|
||||
@@ -115,7 +115,6 @@ namespace FlaxEditor.Gizmo
|
||||
bool isCenter = _activeAxis == Axis.Center;
|
||||
renderContext.View.GetWorldMatrix(ref _gizmoWorld, out Matrix world);
|
||||
|
||||
const sbyte sortOrder = 100; // Draw after any other editor shapes
|
||||
const float gizmoModelsScale2RealGizmoSize = 0.075f;
|
||||
Mesh cubeMesh = _modelCube.LODs[0].Meshes[0];
|
||||
Mesh sphereMesh = _modelSphere.LODs[0].Meshes[0];
|
||||
@@ -137,42 +136,42 @@ namespace FlaxEditor.Gizmo
|
||||
Matrix.RotationY(-Mathf.PiOverTwo, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance xAxisMaterialTransform = gizmoLocked ? _materialAxisLocked : (isXAxis ? _materialAxisFocus : _materialAxisX);
|
||||
transAxisMesh.Draw(ref renderContext, xAxisMaterialTransform, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
transAxisMesh.Draw(ref renderContext, xAxisMaterialTransform, ref m3);
|
||||
|
||||
// Y axis
|
||||
Matrix.RotationX(Mathf.PiOverTwo, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance yAxisMaterialTransform = gizmoLocked ? _materialAxisLocked : (isYAxis ? _materialAxisFocus : _materialAxisY);
|
||||
transAxisMesh.Draw(ref renderContext, yAxisMaterialTransform, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
transAxisMesh.Draw(ref renderContext, yAxisMaterialTransform, ref m3);
|
||||
|
||||
// Z axis
|
||||
Matrix.RotationX(Mathf.Pi, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance zAxisMaterialTransform = gizmoLocked ? _materialAxisLocked : (isZAxis ? _materialAxisFocus : _materialAxisZ);
|
||||
transAxisMesh.Draw(ref renderContext, zAxisMaterialTransform, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
transAxisMesh.Draw(ref renderContext, zAxisMaterialTransform, ref m3);
|
||||
|
||||
// XY plane
|
||||
m2 = Matrix.Transformation(new Vector3(boxSize, boxSize * 0.1f, boxSize), Quaternion.RotationX(Mathf.PiOverTwo), new Vector3(boxSize * boxScale, boxSize * boxScale, 0.0f));
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance xyPlaneMaterialTransform = gizmoLocked ? _materialAxisLocked : (_activeAxis == Axis.XY ? _materialAxisFocus : _materialAxisX);
|
||||
cubeMesh.Draw(ref renderContext, xyPlaneMaterialTransform, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
cubeMesh.Draw(ref renderContext, xyPlaneMaterialTransform, ref m3);
|
||||
|
||||
// ZX plane
|
||||
m2 = Matrix.Transformation(new Vector3(boxSize, boxSize * 0.1f, boxSize), Quaternion.Identity, new Vector3(boxSize * boxScale, 0.0f, boxSize * boxScale));
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance zxPlaneMaterialTransform = gizmoLocked ? _materialAxisLocked : (_activeAxis == Axis.ZX ? _materialAxisFocus : _materialAxisY);
|
||||
cubeMesh.Draw(ref renderContext, zxPlaneMaterialTransform, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
cubeMesh.Draw(ref renderContext, zxPlaneMaterialTransform, ref m3);
|
||||
|
||||
// YZ plane
|
||||
m2 = Matrix.Transformation(new Vector3(boxSize, boxSize * 0.1f, boxSize), Quaternion.RotationZ(Mathf.PiOverTwo), new Vector3(0.0f, boxSize * boxScale, boxSize * boxScale));
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance yzPlaneMaterialTransform = gizmoLocked ? _materialAxisLocked : (_activeAxis == Axis.YZ ? _materialAxisFocus : _materialAxisZ);
|
||||
cubeMesh.Draw(ref renderContext, yzPlaneMaterialTransform, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
cubeMesh.Draw(ref renderContext, yzPlaneMaterialTransform, ref m3);
|
||||
|
||||
// Center sphere
|
||||
Matrix.Scaling(gizmoModelsScale2RealGizmoSize, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
sphereMesh.Draw(ref renderContext, isCenter ? _materialAxisFocus : _materialSphere, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
sphereMesh.Draw(ref renderContext, isCenter ? _materialAxisFocus : _materialSphere, ref m3);
|
||||
|
||||
break;
|
||||
}
|
||||
@@ -187,22 +186,22 @@ namespace FlaxEditor.Gizmo
|
||||
Matrix.RotationZ(Mathf.PiOverTwo, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance xAxisMaterialRotate = gizmoLocked ? _materialAxisLocked : (isXAxis ? _materialAxisFocus : _materialAxisX);
|
||||
rotationAxisMesh.Draw(ref renderContext, xAxisMaterialRotate, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
rotationAxisMesh.Draw(ref renderContext, xAxisMaterialRotate, ref m3);
|
||||
|
||||
// Y axis
|
||||
MaterialInstance yAxisMaterialRotate = gizmoLocked ? _materialAxisLocked : (isYAxis ? _materialAxisFocus : _materialAxisY);
|
||||
rotationAxisMesh.Draw(ref renderContext, yAxisMaterialRotate, ref m1, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
rotationAxisMesh.Draw(ref renderContext, yAxisMaterialRotate, ref m1);
|
||||
|
||||
// Z axis
|
||||
Matrix.RotationX(-Mathf.PiOverTwo, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance zAxisMaterialRotate = gizmoLocked ? _materialAxisLocked : (isZAxis ? _materialAxisFocus : _materialAxisZ);
|
||||
rotationAxisMesh.Draw(ref renderContext, zAxisMaterialRotate, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
rotationAxisMesh.Draw(ref renderContext, zAxisMaterialRotate, ref m3);
|
||||
|
||||
// Center box
|
||||
Matrix.Scaling(gizmoModelsScale2RealGizmoSize, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
sphereMesh.Draw(ref renderContext, isCenter ? _materialAxisFocus : _materialSphere, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
sphereMesh.Draw(ref renderContext, isCenter ? _materialAxisFocus : _materialSphere, ref m3);
|
||||
|
||||
break;
|
||||
}
|
||||
@@ -217,42 +216,42 @@ namespace FlaxEditor.Gizmo
|
||||
Matrix.RotationY(-Mathf.PiOverTwo, out m2);
|
||||
Matrix.Multiply(ref m2, ref mx1, out m3);
|
||||
MaterialInstance xAxisMaterialRotate = gizmoLocked ? _materialAxisLocked : (isXAxis ? _materialAxisFocus : _materialAxisX);
|
||||
scaleAxisMesh.Draw(ref renderContext, xAxisMaterialRotate, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
scaleAxisMesh.Draw(ref renderContext, xAxisMaterialRotate, ref m3);
|
||||
|
||||
// Y axis
|
||||
Matrix.RotationX(Mathf.PiOverTwo, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance yAxisMaterialRotate = gizmoLocked ? _materialAxisLocked : (isYAxis ? _materialAxisFocus : _materialAxisY);
|
||||
scaleAxisMesh.Draw(ref renderContext, yAxisMaterialRotate, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
scaleAxisMesh.Draw(ref renderContext, yAxisMaterialRotate, ref m3);
|
||||
|
||||
// Z axis
|
||||
Matrix.RotationX(Mathf.Pi, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance zAxisMaterialRotate = gizmoLocked ? _materialAxisLocked : (isZAxis ? _materialAxisFocus : _materialAxisZ);
|
||||
scaleAxisMesh.Draw(ref renderContext, zAxisMaterialRotate, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
scaleAxisMesh.Draw(ref renderContext, zAxisMaterialRotate, ref m3);
|
||||
|
||||
// XY plane
|
||||
m2 = Matrix.Transformation(new Vector3(boxSize, boxSize * 0.1f, boxSize), Quaternion.RotationX(Mathf.PiOverTwo), new Vector3(boxSize * boxScale, boxSize * boxScale, 0.0f));
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance xyPlaneMaterialScale = gizmoLocked ? _materialAxisLocked : (_activeAxis == Axis.XY ? _materialAxisFocus : _materialAxisX);
|
||||
cubeMesh.Draw(ref renderContext, xyPlaneMaterialScale, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
cubeMesh.Draw(ref renderContext, xyPlaneMaterialScale, ref m3);
|
||||
|
||||
// ZX plane
|
||||
m2 = Matrix.Transformation(new Vector3(boxSize, boxSize * 0.1f, boxSize), Quaternion.Identity, new Vector3(boxSize * boxScale, 0.0f, boxSize * boxScale));
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance zxPlaneMaterialScale = gizmoLocked ? _materialAxisLocked : (_activeAxis == Axis.ZX ? _materialAxisFocus : _materialAxisZ);
|
||||
cubeMesh.Draw(ref renderContext, zxPlaneMaterialScale, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
cubeMesh.Draw(ref renderContext, zxPlaneMaterialScale, ref m3);
|
||||
|
||||
// YZ plane
|
||||
m2 = Matrix.Transformation(new Vector3(boxSize, boxSize * 0.1f, boxSize), Quaternion.RotationZ(Mathf.PiOverTwo), new Vector3(0.0f, boxSize * boxScale, boxSize * boxScale));
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
MaterialInstance yzPlaneMaterialScale = gizmoLocked ? _materialAxisLocked : (_activeAxis == Axis.YZ ? _materialAxisFocus : _materialAxisY);
|
||||
cubeMesh.Draw(ref renderContext, yzPlaneMaterialScale, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
cubeMesh.Draw(ref renderContext, yzPlaneMaterialScale, ref m3);
|
||||
|
||||
// Center box
|
||||
Matrix.Scaling(gizmoModelsScale2RealGizmoSize, out m2);
|
||||
Matrix.Multiply(ref m2, ref m1, out m3);
|
||||
sphereMesh.Draw(ref renderContext, isCenter ? _materialAxisFocus : _materialSphere, ref m3, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
sphereMesh.Draw(ref renderContext, isCenter ? _materialAxisFocus : _materialSphere, ref m3);
|
||||
|
||||
break;
|
||||
}
|
||||
@@ -264,7 +263,7 @@ namespace FlaxEditor.Gizmo
|
||||
Transform t = _vertexSnapObject?.Transform ?? _vertexSnapObjectTo.Transform;
|
||||
Vector3 p = t.LocalToWorld(_vertexSnapObject != null ? _vertexSnapPoint : _vertexSnapPointTo);
|
||||
Matrix matrix = new Transform(p, t.Orientation, new Float3(gizmoModelsScale2RealGizmoSize)).GetWorld();
|
||||
cubeMesh.Draw(ref renderContext, _materialSphere, ref matrix, StaticFlags.None, true, DrawPass.Default, 0.0f, sortOrder);
|
||||
cubeMesh.Draw(ref renderContext, _materialSphere, ref matrix);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -150,8 +150,7 @@ namespace FlaxEditor
|
||||
private float _mouseMoveSum;
|
||||
private UndoMultiBlock _undoBlock;
|
||||
private View _view;
|
||||
private double[] _gridTickSteps = Utilities.Utils.CurveTickSteps;
|
||||
private float[] _gridTickStrengths;
|
||||
private float[] _gridTickSteps = Utilities.Utils.CurveTickSteps, _gridTickStrengths;
|
||||
private List<Widget> _widgets;
|
||||
private Widget _activeWidget;
|
||||
|
||||
@@ -565,9 +564,9 @@ namespace FlaxEditor
|
||||
var linesColor = style.ForegroundDisabled.RGBMultiplied(0.5f);
|
||||
var labelsColor = style.ForegroundDisabled;
|
||||
var labelsSize = 10.0f;
|
||||
Utilities.Utils.DrawCurveTicks((decimal tick, double step, float strength) =>
|
||||
Utilities.Utils.DrawCurveTicks((float tick, float strength) =>
|
||||
{
|
||||
var p = _view.PointToParent(axis * (float)tick);
|
||||
var p = _view.PointToParent(axis * tick);
|
||||
|
||||
// Draw line
|
||||
var lineRect = new Rectangle
|
||||
|
||||
@@ -504,8 +504,7 @@ DEFINE_INTERNAL_CALL(bool) EditorInternal_CanSetToRoot(Prefab* prefab, Actor* ta
|
||||
return false;
|
||||
const ISerializable::DeserializeStream& newRootData = **newRootDataPtr;
|
||||
Guid prefabId, prefabObjectID;
|
||||
if (JsonTools::GetGuidIfValid(prefabId, newRootData, "PrefabID") &&
|
||||
JsonTools::GetGuidIfValid(prefabObjectID, newRootData, "PrefabObjectID"))
|
||||
if (JsonTools::GetGuidIfValid(prefabId, newRootData, "PrefabID") && JsonTools::GetGuidIfValid(prefabObjectID, newRootData, "PrefabObjectID"))
|
||||
{
|
||||
const auto nestedPrefab = Content::Load<Prefab>(prefabId);
|
||||
if (nestedPrefab && nestedPrefab->GetRootObjectId() != prefabObjectID)
|
||||
@@ -515,6 +514,21 @@ DEFINE_INTERNAL_CALL(bool) EditorInternal_CanSetToRoot(Prefab* prefab, Actor* ta
|
||||
return true;
|
||||
}
|
||||
|
||||
DEFINE_INTERNAL_CALL(void) EditorInternal_GetPrefabNestedObject(Guid* prefabId, Guid* prefabObjectId, Guid* outPrefabId, Guid* outPrefabObjectId)
|
||||
{
|
||||
*outPrefabId = Guid::Empty;
|
||||
*outPrefabObjectId = Guid::Empty;
|
||||
const auto prefab = Content::Load<Prefab>(*prefabId);
|
||||
if (!prefab)
|
||||
return;
|
||||
const ISerializable::DeserializeStream** prefabObjectDataPtr = prefab->ObjectsDataCache.TryGet(*prefabObjectId);
|
||||
if (!prefabObjectDataPtr)
|
||||
return;
|
||||
const ISerializable::DeserializeStream& prefabObjectData = **prefabObjectDataPtr;
|
||||
JsonTools::GetGuidIfValid(*outPrefabId, prefabObjectData, "PrefabID");
|
||||
JsonTools::GetGuidIfValid(*outPrefabObjectId, prefabObjectData, "PrefabObjectID");
|
||||
}
|
||||
|
||||
DEFINE_INTERNAL_CALL(float) EditorInternal_GetAnimationTime(AnimatedModel* animatedModel)
|
||||
{
|
||||
return animatedModel && animatedModel->GraphInstance.State.Count() == 1 ? animatedModel->GraphInstance.State[0].Animation.TimePosition : 0.0f;
|
||||
|
||||
@@ -12,14 +12,11 @@
|
||||
#include "Engine/Scripting/ManagedCLR/MException.h"
|
||||
#include "Engine/Scripting/Internal/MainThreadManagedInvokeAction.h"
|
||||
#include "Engine/Content/Assets/VisualScript.h"
|
||||
#include "Engine/Content/Content.h"
|
||||
#include "Engine/CSG/CSGBuilder.h"
|
||||
#include "Engine/Engine/CommandLine.h"
|
||||
#include "Engine/Renderer/ProbesRenderer.h"
|
||||
#include "Engine/Animations/Graph/AnimGraph.h"
|
||||
#include "Engine/Core/ObjectsRemovalService.h"
|
||||
#include "Engine/Level/Prefabs/Prefab.h"
|
||||
#include "Engine/Serialization/JsonTools.h"
|
||||
|
||||
ManagedEditor::InternalOptions ManagedEditor::ManagedEditorOptions;
|
||||
|
||||
@@ -595,7 +592,6 @@ bool ManagedEditor::EvaluateVisualScriptLocal(VisualScript* script, VisualScript
|
||||
|
||||
void ManagedEditor::WipeOutLeftoverSceneObjects()
|
||||
{
|
||||
PROFILE_CPU();
|
||||
Array<ScriptingObject*> objects = Scripting::GetObjects();
|
||||
bool removedAny = false;
|
||||
for (ScriptingObject* object : objects)
|
||||
@@ -617,21 +613,6 @@ void ManagedEditor::WipeOutLeftoverSceneObjects()
|
||||
ObjectsRemovalService::Flush();
|
||||
}
|
||||
|
||||
void ManagedEditor::GetPrefabNestedObject(const Guid& prefabId, const Guid& prefabObjectId, Guid& outPrefabId, Guid& outPrefabObjectId)
|
||||
{
|
||||
outPrefabId = Guid::Empty;
|
||||
outPrefabObjectId = Guid::Empty;
|
||||
const auto prefab = Content::Load<Prefab>(prefabId);
|
||||
if (!prefab)
|
||||
return;
|
||||
const ISerializable::DeserializeStream** prefabObjectDataPtr = prefab->ObjectsDataCache.TryGet(prefabObjectId);
|
||||
if (!prefabObjectDataPtr)
|
||||
return;
|
||||
const ISerializable::DeserializeStream& prefabObjectData = **prefabObjectDataPtr;
|
||||
JsonTools::GetGuidIfValid(outPrefabId, prefabObjectData, "PrefabID");
|
||||
JsonTools::GetGuidIfValid(outPrefabObjectId, prefabObjectData, "PrefabObjectID");
|
||||
}
|
||||
|
||||
void ManagedEditor::OnEditorAssemblyLoaded(MAssembly* assembly)
|
||||
{
|
||||
ASSERT(!HasManagedInstance());
|
||||
|
||||
@@ -259,7 +259,6 @@ public:
|
||||
API_FUNCTION(Internal) static Array<VisualScriptLocal> GetVisualScriptLocals();
|
||||
API_FUNCTION(Internal) static bool EvaluateVisualScriptLocal(VisualScript* script, API_PARAM(Ref) VisualScriptLocal& local);
|
||||
API_FUNCTION(Internal) static void WipeOutLeftoverSceneObjects();
|
||||
API_FUNCTION(Internal) static void GetPrefabNestedObject(API_PARAM(Ref) const Guid& prefabId, API_PARAM(Ref) const Guid& prefabObjectId, API_PARAM(Out) Guid& outPrefabId, API_PARAM(Out) Guid& outPrefabObjectId);
|
||||
|
||||
private:
|
||||
void OnEditorAssemblyLoaded(MAssembly* assembly);
|
||||
|
||||
@@ -21,7 +21,6 @@ namespace FlaxEditor.Modules
|
||||
private bool _enableEvents;
|
||||
private bool _isDuringFastSetup;
|
||||
private bool _rebuildFlag;
|
||||
private bool _rebuildInitFlag;
|
||||
private int _itemsCreated;
|
||||
private int _itemsDeleted;
|
||||
private readonly HashSet<MainContentTreeNode> _dirtyNodes = new HashSet<MainContentTreeNode>();
|
||||
@@ -62,7 +61,7 @@ namespace FlaxEditor.Modules
|
||||
public event Action WorkspaceModified;
|
||||
|
||||
/// <summary>
|
||||
/// Occurs when workspace will be rebuilt.
|
||||
/// Occurs when workspace has will be rebuilt.
|
||||
/// </summary>
|
||||
public event Action WorkspaceRebuilding;
|
||||
|
||||
@@ -89,9 +88,6 @@ namespace FlaxEditor.Modules
|
||||
|
||||
// Register AssetItems serialization helper (serialize ref ID only)
|
||||
FlaxEngine.Json.JsonSerializer.Settings.Converters.Add(new AssetItemConverter());
|
||||
|
||||
ScriptsBuilder.ScriptsReload += OnScriptsReload;
|
||||
ScriptsBuilder.ScriptsReloadEnd += OnScriptsReloadEnd;
|
||||
}
|
||||
|
||||
private void OnContentAssetDisposing(Asset asset)
|
||||
@@ -821,7 +817,6 @@ namespace FlaxEditor.Modules
|
||||
Profiler.BeginEvent("ContentDatabase.Rebuild");
|
||||
var startTime = Platform.TimeSeconds;
|
||||
_rebuildFlag = false;
|
||||
_rebuildInitFlag = false;
|
||||
_enableEvents = false;
|
||||
|
||||
// Load all folders
|
||||
@@ -1235,6 +1230,8 @@ namespace FlaxEditor.Modules
|
||||
LoadProjects(Game.Project);
|
||||
}
|
||||
|
||||
RebuildInternal();
|
||||
|
||||
Editor.ContentImporting.ImportFileEnd += (obj, failed) =>
|
||||
{
|
||||
var path = obj.ResultUrl;
|
||||
@@ -1242,15 +1239,6 @@ namespace FlaxEditor.Modules
|
||||
FlaxEngine.Scripting.InvokeOnUpdate(() => OnImportFileDone(path));
|
||||
};
|
||||
_enableEvents = true;
|
||||
_rebuildInitFlag = true;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void OnEndInit()
|
||||
{
|
||||
// Handle init when project was loaded without scripts loading ()
|
||||
if (_rebuildInitFlag)
|
||||
RebuildInternal();
|
||||
}
|
||||
|
||||
private void OnImportFileDone(string path)
|
||||
@@ -1325,52 +1313,6 @@ namespace FlaxEditor.Modules
|
||||
}
|
||||
}
|
||||
|
||||
private void OnScriptsReload()
|
||||
{
|
||||
var enabledEvents = _enableEvents;
|
||||
_enableEvents = false;
|
||||
_isDuringFastSetup = true;
|
||||
var startItems = _itemsCreated;
|
||||
foreach (var project in Projects)
|
||||
{
|
||||
if (project.Content != null)
|
||||
{
|
||||
//Dispose(project.Content.Folder);
|
||||
for (int i = 0; i < project.Content.Folder.Children.Count; i++)
|
||||
{
|
||||
Dispose(project.Content.Folder.Children[i]);
|
||||
i--;
|
||||
}
|
||||
}
|
||||
if (project.Source != null)
|
||||
{
|
||||
//Dispose(project.Source.Folder);
|
||||
for (int i = 0; i < project.Source.Folder.Children.Count; i++)
|
||||
{
|
||||
Dispose(project.Source.Folder.Children[i]);
|
||||
i--;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
List<ContentProxy> removeProxies = new List<ContentProxy>();
|
||||
foreach (var proxy in Editor.Instance.ContentDatabase.Proxy)
|
||||
{
|
||||
if (proxy.GetType().IsCollectible)
|
||||
removeProxies.Add(proxy);
|
||||
}
|
||||
foreach (var proxy in removeProxies)
|
||||
RemoveProxy(proxy, false);
|
||||
|
||||
_isDuringFastSetup = false;
|
||||
_enableEvents = enabledEvents;
|
||||
}
|
||||
|
||||
private void OnScriptsReloadEnd()
|
||||
{
|
||||
RebuildInternal();
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void OnUpdate()
|
||||
{
|
||||
@@ -1398,8 +1340,6 @@ namespace FlaxEditor.Modules
|
||||
public override void OnExit()
|
||||
{
|
||||
FlaxEngine.Content.AssetDisposing -= OnContentAssetDisposing;
|
||||
ScriptsBuilder.ScriptsReload -= OnScriptsReload;
|
||||
ScriptsBuilder.ScriptsReloadEnd -= OnScriptsReloadEnd;
|
||||
|
||||
// Disable events
|
||||
_enableEvents = false;
|
||||
|
||||
@@ -391,20 +391,6 @@ namespace FlaxEditor.Modules
|
||||
public override void OnInit()
|
||||
{
|
||||
ImportFileEntry.RegisterDefaultTypes();
|
||||
ScriptsBuilder.ScriptsReloadBegin += OnScriptsReloadBegin;
|
||||
}
|
||||
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
// Remove import file types from scripting assemblies
|
||||
List<string> removeFileTypes = new List<string>();
|
||||
foreach (var pair in ImportFileEntry.FileTypes)
|
||||
{
|
||||
if (pair.Value.Method.IsCollectible || (pair.Value.Target != null && pair.Value.Target.GetType().IsCollectible))
|
||||
removeFileTypes.Add(pair.Key);
|
||||
}
|
||||
foreach (var fileType in removeFileTypes)
|
||||
ImportFileEntry.FileTypes.Remove(fileType);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
@@ -465,7 +451,6 @@ namespace FlaxEditor.Modules
|
||||
/// <inheritdoc />
|
||||
public override void OnExit()
|
||||
{
|
||||
ScriptsBuilder.ScriptsReloadBegin -= OnScriptsReloadBegin;
|
||||
EndWorker();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -105,33 +105,6 @@ namespace FlaxEditor.Modules
|
||||
Editor.Windows.ContentWin.NewItem(proxy, actor, contentItem => OnPrefabCreated(contentItem, actor, prefabWindow), actor.Name, rename);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens a prefab editor window.
|
||||
/// </summary>
|
||||
public void OpenPrefab(ActorNode actorNode)
|
||||
{
|
||||
if (actorNode != null)
|
||||
OpenPrefab(actorNode.Actor.PrefabID);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opens a prefab editor window.
|
||||
/// </summary>
|
||||
public void OpenPrefab(Guid prefabID = default)
|
||||
{
|
||||
if (prefabID == Guid.Empty)
|
||||
{
|
||||
var selection = Editor.SceneEditing.Selection.Where(x => x is ActorNode actorNode && actorNode.HasPrefabLink).ToList().BuildNodesParents();
|
||||
if (selection.Count == 0 || !((ActorNode)selection[0]).Actor.HasPrefabLink)
|
||||
return;
|
||||
prefabID = ((ActorNode)selection[0]).Actor.PrefabID;
|
||||
}
|
||||
|
||||
var item = Editor.ContentDatabase.Find(prefabID);
|
||||
if (item != null)
|
||||
Editor.ContentEditing.Open(item);
|
||||
}
|
||||
|
||||
private void OnPrefabCreated(ContentItem contentItem, Actor actor, Windows.Assets.PrefabWindow prefabWindow)
|
||||
{
|
||||
if (contentItem is PrefabItem prefabItem)
|
||||
|
||||
@@ -58,7 +58,7 @@ namespace FlaxEditor.Modules
|
||||
: base(editor)
|
||||
{
|
||||
// After editor cache but before the windows
|
||||
InitOrder = -800;
|
||||
InitOrder = -900;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -160,7 +160,7 @@ namespace FlaxEditor.Modules
|
||||
internal UIModule(Editor editor)
|
||||
: base(editor)
|
||||
{
|
||||
InitOrder = -70;
|
||||
InitOrder = -90;
|
||||
VisjectSurfaceBackground = FlaxEngine.Content.LoadAsyncInternal<Texture>("Editor/VisjectSurface");
|
||||
ColorValueBox.ShowPickColorDialog += ShowPickColorDialog;
|
||||
}
|
||||
|
||||
@@ -5,12 +5,10 @@ using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.IO;
|
||||
using System.Reflection;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Text;
|
||||
using System.Xml;
|
||||
using FlaxEditor.Content;
|
||||
using FlaxEditor.GUI.Dialogs;
|
||||
using FlaxEditor.GUI.Docking;
|
||||
using FlaxEditor.Windows;
|
||||
using FlaxEditor.Windows.Assets;
|
||||
using FlaxEditor.Windows.Profiler;
|
||||
@@ -41,7 +39,6 @@ namespace FlaxEditor.Modules
|
||||
|
||||
public DockState DockState;
|
||||
public DockPanel DockedTo;
|
||||
public int DockedTabIndex;
|
||||
public float? SplitterValue = null;
|
||||
|
||||
public bool SelectOnShow = false;
|
||||
@@ -51,8 +48,6 @@ namespace FlaxEditor.Modules
|
||||
public Float2 FloatSize;
|
||||
public Float2 FloatPosition;
|
||||
|
||||
public Guid AssetItemID;
|
||||
|
||||
// Constructor, to allow for default values
|
||||
public WindowRestoreData()
|
||||
{
|
||||
@@ -810,64 +805,43 @@ namespace FlaxEditor.Modules
|
||||
Level.SceneSaving += OnSceneSaving;
|
||||
Level.SceneUnloaded += OnSceneUnloaded;
|
||||
Level.SceneUnloading += OnSceneUnloading;
|
||||
Editor.ContentDatabase.WorkspaceRebuilt += OnWorkspaceRebuilt;
|
||||
ScriptsBuilder.ScriptsReloadEnd += OnScriptsReloadEnd;
|
||||
Editor.StateMachine.StateChanged += OnEditorStateChanged;
|
||||
}
|
||||
|
||||
internal void AddToRestore(AssetEditorWindow win)
|
||||
{
|
||||
AddToRestore(win, win.GetType(), new WindowRestoreData
|
||||
{
|
||||
AssetItemID = win.Item.ID,
|
||||
});
|
||||
}
|
||||
|
||||
internal void AddToRestore(CustomEditorWindow win)
|
||||
{
|
||||
AddToRestore(win.Window, win.GetType(), new WindowRestoreData());
|
||||
}
|
||||
var type = win.GetType();
|
||||
|
||||
private void AddToRestore(EditorWindow win, Type type, WindowRestoreData winData)
|
||||
{
|
||||
// Validate if can restore type
|
||||
var constructor = type.GetConstructor(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, Type.EmptyTypes, null);
|
||||
if (constructor == null || type.IsGenericType)
|
||||
return;
|
||||
|
||||
var panel = win.ParentDockPanel;
|
||||
var winData = new WindowRestoreData();
|
||||
var panel = win.Window.ParentDockPanel;
|
||||
|
||||
// Ensure that this window is only selected following recompilation
|
||||
// if it was the active tab in its dock panel. Otherwise, there is a
|
||||
// risk of interrupting the user's workflow by potentially selecting
|
||||
// background tabs.
|
||||
var window = win.RootWindow.Window;
|
||||
winData.SelectOnShow = panel.SelectedTab == win;
|
||||
winData.DockedTabIndex = 0;
|
||||
if (panel is FloatWindowDockPanel && window != null && panel.TabsCount == 1)
|
||||
winData.SelectOnShow = panel.SelectedTab == win.Window;
|
||||
if (panel is FloatWindowDockPanel)
|
||||
{
|
||||
winData.DockState = DockState.Float;
|
||||
var window = win.Window.RootWindow.Window;
|
||||
winData.FloatPosition = window.Position;
|
||||
winData.FloatSize = window.ClientSize;
|
||||
winData.Maximize = window.IsMaximized;
|
||||
winData.Minimize = window.IsMinimized;
|
||||
winData.DockedTo = panel;
|
||||
}
|
||||
else
|
||||
{
|
||||
for (int i = 0; i < panel.Tabs.Count; i++)
|
||||
{
|
||||
if (panel.Tabs[i] == win)
|
||||
{
|
||||
winData.DockedTabIndex = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (panel.TabsCount > 1)
|
||||
{
|
||||
winData.DockState = DockState.DockFill;
|
||||
winData.DockedTo = panel;
|
||||
}
|
||||
else
|
||||
}else
|
||||
{
|
||||
winData.DockState = panel.TryGetDockState(out var splitterValue);
|
||||
winData.DockedTo = panel.ParentDockPanel;
|
||||
@@ -879,93 +853,38 @@ namespace FlaxEditor.Modules
|
||||
_restoreWindows.Add(winData);
|
||||
}
|
||||
|
||||
private void OnWorkspaceRebuilt()
|
||||
private void OnScriptsReloadEnd()
|
||||
{
|
||||
// Go in reverse order to create floating Prefab windows first before docked windows
|
||||
for (int i = _restoreWindows.Count - 1; i >= 0; i--)
|
||||
for (int i = 0; i < _restoreWindows.Count; i++)
|
||||
{
|
||||
var winData = _restoreWindows[i];
|
||||
|
||||
try
|
||||
{
|
||||
var assembly = Utils.GetAssemblyByName(winData.AssemblyName);
|
||||
if (assembly == null)
|
||||
continue;
|
||||
|
||||
var type = assembly.GetType(winData.TypeName);
|
||||
if (type == null)
|
||||
continue;
|
||||
|
||||
if (type.IsAssignableTo(typeof(AssetEditorWindow)))
|
||||
if (assembly != null)
|
||||
{
|
||||
var ctor = type.GetConstructor(new Type[] { typeof(Editor), typeof(AssetItem) });
|
||||
var assetItem = Editor.ContentDatabase.FindAsset(winData.AssetItemID);
|
||||
var win = (AssetEditorWindow)ctor.Invoke(new object[] { Editor.Instance, assetItem });
|
||||
win.Show(winData.DockState, winData.DockState != DockState.Float ? winData.DockedTo : null, winData.SelectOnShow, winData.SplitterValue);
|
||||
if (winData.DockState == DockState.Float)
|
||||
var type = assembly.GetType(winData.TypeName);
|
||||
if (type != null)
|
||||
{
|
||||
var window = win.RootWindow.Window;
|
||||
window.Position = winData.FloatPosition;
|
||||
if (winData.Maximize)
|
||||
var win = (CustomEditorWindow)Activator.CreateInstance(type);
|
||||
win.Show(winData.DockState, winData.DockedTo, winData.SelectOnShow, winData.SplitterValue);
|
||||
if (winData.DockState == DockState.Float)
|
||||
{
|
||||
window.Maximize();
|
||||
}
|
||||
else if (winData.Minimize)
|
||||
{
|
||||
window.Minimize();
|
||||
}
|
||||
else
|
||||
{
|
||||
window.ClientSize = winData.FloatSize;
|
||||
}
|
||||
|
||||
// Update panel reference in other windows docked to this panel
|
||||
foreach (ref var otherData in CollectionsMarshal.AsSpan(_restoreWindows))
|
||||
{
|
||||
if (otherData.DockedTo == winData.DockedTo)
|
||||
otherData.DockedTo = win.ParentDockPanel;
|
||||
}
|
||||
}
|
||||
var panel = win.ParentDockPanel;
|
||||
int currentTabIndex = 0;
|
||||
for (int pi = 0; pi < panel.TabsCount; pi++)
|
||||
{
|
||||
if (panel.Tabs[pi] == win)
|
||||
{
|
||||
currentTabIndex = pi;
|
||||
break;
|
||||
}
|
||||
}
|
||||
while (currentTabIndex > winData.DockedTabIndex)
|
||||
{
|
||||
win.ParentDockPanel.MoveTabLeft(currentTabIndex);
|
||||
currentTabIndex--;
|
||||
}
|
||||
while (currentTabIndex < winData.DockedTabIndex)
|
||||
{
|
||||
win.ParentDockPanel.MoveTabRight(currentTabIndex);
|
||||
currentTabIndex++;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
var win = (CustomEditorWindow)Activator.CreateInstance(type);
|
||||
win.Show(winData.DockState, winData.DockedTo, winData.SelectOnShow, winData.SplitterValue);
|
||||
if (winData.DockState == DockState.Float)
|
||||
{
|
||||
var window = win.Window.RootWindow.Window;
|
||||
window.Position = winData.FloatPosition;
|
||||
if (winData.Maximize)
|
||||
{
|
||||
window.Maximize();
|
||||
}
|
||||
else if (winData.Minimize)
|
||||
{
|
||||
window.Minimize();
|
||||
}
|
||||
else
|
||||
{
|
||||
window.ClientSize = winData.FloatSize;
|
||||
var window = win.Window.RootWindow.Window;
|
||||
window.Position = winData.FloatPosition;
|
||||
if (winData.Maximize)
|
||||
{
|
||||
window.Maximize();
|
||||
}
|
||||
else if (winData.Minimize)
|
||||
{
|
||||
window.Minimize();
|
||||
}
|
||||
else
|
||||
{
|
||||
window.ClientSize = winData.FloatSize;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -976,11 +895,6 @@ namespace FlaxEditor.Modules
|
||||
Editor.LogWarning(string.Format("Failed to restore window {0} (assembly: {1})", winData.TypeName, winData.AssemblyName));
|
||||
}
|
||||
}
|
||||
|
||||
// Restored windows stole the focus from Editor
|
||||
if (_restoreWindows.Count > 0)
|
||||
Editor.Instance.Windows.MainWindow.Focus();
|
||||
|
||||
_restoreWindows.Clear();
|
||||
}
|
||||
|
||||
@@ -1136,7 +1050,7 @@ namespace FlaxEditor.Modules
|
||||
Level.SceneSaving -= OnSceneSaving;
|
||||
Level.SceneUnloaded -= OnSceneUnloaded;
|
||||
Level.SceneUnloading -= OnSceneUnloading;
|
||||
Editor.ContentDatabase.WorkspaceRebuilt -= OnWorkspaceRebuilt;
|
||||
ScriptsBuilder.ScriptsReloadEnd -= OnScriptsReloadEnd;
|
||||
Editor.StateMachine.StateChanged -= OnEditorStateChanged;
|
||||
|
||||
// Close main window
|
||||
|
||||
@@ -8,7 +8,6 @@ using FlaxEditor.CustomEditors;
|
||||
using FlaxEditor.CustomEditors.Elements;
|
||||
using FlaxEngine;
|
||||
using FlaxEngine.GUI;
|
||||
using static FlaxEditor.Viewport.EditorViewport;
|
||||
|
||||
namespace FlaxEditor.Options
|
||||
{
|
||||
@@ -19,7 +18,7 @@ namespace FlaxEditor.Options
|
||||
[HideInEditor]
|
||||
[TypeConverter(typeof(InputBindingConverter))]
|
||||
[CustomEditor(typeof(InputBindingEditor))]
|
||||
public struct InputBinding : IEquatable<InputBinding>
|
||||
public struct InputBinding
|
||||
{
|
||||
/// <summary>
|
||||
/// The key to bind.
|
||||
@@ -252,40 +251,6 @@ namespace FlaxEditor.Options
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public bool Equals(InputBinding other)
|
||||
{
|
||||
return Key == other.Key && Modifier1 == other.Modifier1 && Modifier2 == other.Modifier2;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override bool Equals(object obj)
|
||||
{
|
||||
return obj is InputBinding other && Equals(other);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override int GetHashCode()
|
||||
{
|
||||
return HashCode.Combine((int)Key, (int)Modifier1, (int)Modifier2);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compares two values.
|
||||
/// </summary>
|
||||
public static bool operator ==(InputBinding left, InputBinding right)
|
||||
{
|
||||
return left.Equals(right);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compares two values.
|
||||
/// </summary>
|
||||
public static bool operator !=(InputBinding left, InputBinding right)
|
||||
{
|
||||
return !left.Equals(right);
|
||||
}
|
||||
}
|
||||
|
||||
class InputBindingConverter : TypeConverter
|
||||
@@ -557,27 +522,5 @@ namespace FlaxEditor.Options
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Invokes a specific binding.
|
||||
/// </summary>
|
||||
/// <param name="editor">The editor instance.</param>
|
||||
/// <param name="binding">The binding to execute.</param>
|
||||
/// <returns>True if event has been handled, otherwise false.</returns>
|
||||
public bool Invoke(Editor editor, InputBinding binding)
|
||||
{
|
||||
if (binding == new InputBinding())
|
||||
return false;
|
||||
var options = editor.Options.Options.Input;
|
||||
for (int i = 0; i < Bindings.Count; i++)
|
||||
{
|
||||
if (Bindings[i].Binder(options) == binding)
|
||||
{
|
||||
Bindings[i].Callback();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,32 +7,6 @@ using FlaxEngine;
|
||||
|
||||
namespace FlaxEditor.Options
|
||||
{
|
||||
/// <summary>
|
||||
/// Action to perform when a Scene Node receive a double mouse left click.
|
||||
/// </summary>
|
||||
public enum SceneNodeDoubleClick
|
||||
{
|
||||
/// <summary>
|
||||
/// Toggles expand/state of the node.
|
||||
/// </summary>
|
||||
Expand,
|
||||
|
||||
/// <summary>
|
||||
/// Rename the node.
|
||||
/// </summary>
|
||||
RenameActor,
|
||||
|
||||
/// <summary>
|
||||
/// Focus the object in the viewport.
|
||||
/// </summary>
|
||||
FocusActor,
|
||||
|
||||
/// <summary>
|
||||
/// If possible, open the scene node in an associated Editor (eg. Prefab Editor).
|
||||
/// </summary>
|
||||
OpenPrefab,
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Input editor options data container.
|
||||
/// </summary>
|
||||
@@ -370,10 +344,6 @@ namespace FlaxEditor.Options
|
||||
[EditorDisplay("Interface"), EditorOrder(2020)]
|
||||
public InputBinding PreviousTab = new InputBinding(KeyboardKeys.Tab, KeyboardKeys.Control, KeyboardKeys.Shift);
|
||||
|
||||
[DefaultValue(SceneNodeDoubleClick.Expand)]
|
||||
[EditorDisplay("Interface"), EditorOrder(2030)]
|
||||
public SceneNodeDoubleClick DoubleClickSceneNode = SceneNodeDoubleClick.Expand;
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
|
||||
@@ -157,7 +157,7 @@ namespace FlaxEditor.Options
|
||||
/// <summary>
|
||||
/// Focus the Game Window. On play mode end restore focus to the previous window.
|
||||
/// </summary>
|
||||
GameWindowThenRestore,
|
||||
GameWindowThenRestore,
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -379,22 +379,6 @@ namespace FlaxEditor.Options
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the output log text color for warnings
|
||||
/// </summary>
|
||||
[DefaultValue(typeof(Color), "1,1,0,1")]
|
||||
[EditorDisplay("Output Log", "Warning Color"), EditorOrder(446), Tooltip("The output log text color for warnings.")]
|
||||
public Color OutputLogWarningTextColor { get; set; } = Color.Yellow;
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the output log text color for errors
|
||||
/// </summary>
|
||||
[DefaultValue(typeof(Color), "1,0,0,1")]
|
||||
[EditorDisplay("Output Log", "Error Color"), EditorOrder(445), Tooltip("The output log text color for errors.")]
|
||||
public Color OutputLogErrorTextColor { get; set; } = Color.Red;
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a value indicating whether auto-focus output log window on code compilation error.
|
||||
/// </summary>
|
||||
|
||||
@@ -8,7 +8,6 @@ using FlaxEditor.Content;
|
||||
using FlaxEditor.GUI;
|
||||
using FlaxEditor.GUI.Drag;
|
||||
using FlaxEditor.GUI.Tree;
|
||||
using FlaxEditor.Options;
|
||||
using FlaxEditor.Scripting;
|
||||
using FlaxEditor.Utilities;
|
||||
using FlaxEditor.Windows;
|
||||
@@ -16,6 +15,7 @@ using FlaxEditor.Windows.Assets;
|
||||
using FlaxEngine;
|
||||
using FlaxEngine.GUI;
|
||||
using FlaxEngine.Utilities;
|
||||
using Object = FlaxEngine.Object;
|
||||
|
||||
namespace FlaxEditor.SceneGraph.GUI
|
||||
{
|
||||
@@ -393,7 +393,7 @@ namespace FlaxEditor.SceneGraph.GUI
|
||||
/// <summary>
|
||||
/// Starts the actor renaming action.
|
||||
/// </summary>
|
||||
public void StartRenaming(EditorWindow window = null, Panel treePanel = null)
|
||||
public void StartRenaming(EditorWindow window, Panel treePanel = null)
|
||||
{
|
||||
// Block renaming during scripts reload
|
||||
if (Editor.Instance.ProgressReporting.CompileScripts.IsActive)
|
||||
@@ -461,30 +461,6 @@ namespace FlaxEditor.SceneGraph.GUI
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override bool OnMouseDoubleClickHeader(ref Float2 location, MouseButton button)
|
||||
{
|
||||
if (button == MouseButton.Left)
|
||||
{
|
||||
var sceneContext = this.GetSceneContext();
|
||||
switch (Editor.Instance.Options.Options.Input.DoubleClickSceneNode)
|
||||
{
|
||||
case SceneNodeDoubleClick.RenameActor:
|
||||
sceneContext.RenameSelection();
|
||||
return true;
|
||||
case SceneNodeDoubleClick.FocusActor:
|
||||
sceneContext.FocusSelection();
|
||||
return true;
|
||||
case SceneNodeDoubleClick.OpenPrefab:
|
||||
Editor.Instance.Prefabs.OpenPrefab(ActorNode);
|
||||
return true;
|
||||
case SceneNodeDoubleClick.Expand:
|
||||
default: break;
|
||||
}
|
||||
}
|
||||
return base.OnMouseDoubleClickHeader(ref location, button);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override DragDropEffect OnDragEnterHeader(DragData data)
|
||||
{
|
||||
|
||||
@@ -469,7 +469,6 @@ namespace FlaxEditor.SceneGraph
|
||||
{
|
||||
ChildNodes[i].OnDispose();
|
||||
}
|
||||
ChildNodes.Clear();
|
||||
|
||||
SceneGraphFactory.Nodes.Remove(ID);
|
||||
}
|
||||
|
||||
@@ -161,8 +161,6 @@ namespace FlaxEditor.Surface
|
||||
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
_nodesCache.Clear();
|
||||
|
||||
// Check if any of the nodes comes from the game scripts - those can be reloaded at runtime so prevent crashes
|
||||
bool hasTypeFromGameScripts = Editor.Instance.CodeEditing.AnimGraphNodes.HasTypeFromGameScripts;
|
||||
|
||||
|
||||
@@ -1182,9 +1182,9 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void DrawEditorGrid(ref Rectangle rect)
|
||||
public override void DrawEditorBackground(ref Rectangle rect)
|
||||
{
|
||||
base.DrawEditorGrid(ref rect);
|
||||
base.DrawEditorBackground(ref rect);
|
||||
|
||||
// Draw triangulated multi blend space
|
||||
var style = Style.Current;
|
||||
@@ -1195,8 +1195,15 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
else
|
||||
Render2D.FillTriangles(_triangles, style.TextBoxBackgroundSelected.AlphaMultiplied(0.6f));
|
||||
Render2D.DrawTriangles(_triangles, style.Foreground);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void DrawEditorGrid(ref Rectangle rect)
|
||||
{
|
||||
base.DrawEditorGrid(ref rect);
|
||||
|
||||
// Highlight selected blend point
|
||||
var style = Style.Current;
|
||||
var selectedIndex = _selectedAnimation.SelectedIndex;
|
||||
if (selectedIndex != -1 && selectedIndex < _editor.BlendPoints.Count && (ContainsFocus || IsMouseOver))
|
||||
{
|
||||
|
||||
@@ -87,17 +87,11 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
private class GradientStop : Control
|
||||
{
|
||||
private bool _isMoving;
|
||||
private float _movedToTime = float.MaxValue;
|
||||
private Float2 _startMovePos;
|
||||
|
||||
public ColorGradientNode Node;
|
||||
public Color Color;
|
||||
|
||||
public void UpdateLocation(float time)
|
||||
{
|
||||
Location = Node._gradient.BottomLeft + new Float2(time * Node._gradient.Width - Width * 0.5f, 0.0f);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void Draw()
|
||||
{
|
||||
@@ -124,7 +118,6 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
if (button == MouseButton.Left)
|
||||
{
|
||||
Node.Select(this);
|
||||
_movedToTime = float.MaxValue;
|
||||
_isMoving = true;
|
||||
_startMovePos = location;
|
||||
StartMouseCapture();
|
||||
@@ -140,12 +133,6 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
if (button == MouseButton.Left && _isMoving)
|
||||
{
|
||||
_isMoving = false;
|
||||
if (_movedToTime < float.MaxValue)
|
||||
{
|
||||
int index = Node._stops.IndexOf(this);
|
||||
Node.SetStopTime(index, _movedToTime);
|
||||
_movedToTime = float.MaxValue;
|
||||
}
|
||||
EndMouseCapture();
|
||||
}
|
||||
|
||||
@@ -172,10 +159,9 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
if (_isMoving && Float2.DistanceSquared(ref location, ref _startMovePos) > 25.0f)
|
||||
{
|
||||
_startMovePos = Float2.Minimum;
|
||||
int index = Node._stops.IndexOf(this);
|
||||
_movedToTime = (PointToParent(location).X - Node._gradient.BottomLeft.X) / Node._gradient.Width;
|
||||
_movedToTime = Node.ClampStopTime(index, _movedToTime);
|
||||
UpdateLocation(_movedToTime);
|
||||
var index = Node._stops.IndexOf(this);
|
||||
var time = (PointToParent(location).X - Node._gradient.BottomLeft.X) / Node._gradient.Width;
|
||||
Node.SetStopTime(index, time);
|
||||
}
|
||||
|
||||
base.OnMouseMove(location);
|
||||
@@ -185,7 +171,6 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
public override void OnEndMouseCapture()
|
||||
{
|
||||
_isMoving = false;
|
||||
_movedToTime = float.MaxValue;
|
||||
|
||||
base.OnEndMouseCapture();
|
||||
}
|
||||
@@ -238,7 +223,6 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
Parent = this
|
||||
};
|
||||
_timeValue.ValueChanged += OnTimeValueChanged;
|
||||
_timeValue.SlidingEnd += OnTimeValueChanged;
|
||||
|
||||
_colorValue = new ColorValueBox(Color.Black, _timeValue.Right + 4.0f, controlsLevel)
|
||||
{
|
||||
@@ -317,16 +301,8 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
|
||||
private void OnTimeValueChanged()
|
||||
{
|
||||
var time = _timeValue.Value;
|
||||
var index = _stops.IndexOf(_selected);
|
||||
if (_timeValue.IsSliding)
|
||||
{
|
||||
// Preview-only while sliding
|
||||
time = ClampStopTime(index, time);
|
||||
_selected.UpdateLocation(time);
|
||||
return;
|
||||
}
|
||||
SetStopTime(index, time);
|
||||
SetStopTime(index, _timeValue.Value);
|
||||
}
|
||||
|
||||
private void OnColorValueChanged()
|
||||
@@ -370,7 +346,7 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
UpdateStops();
|
||||
}
|
||||
|
||||
private float ClampStopTime(int index, float time)
|
||||
private void SetStopTime(int index, float time)
|
||||
{
|
||||
time = Mathf.Saturate(time);
|
||||
if (index != 0)
|
||||
@@ -381,12 +357,6 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
{
|
||||
time = Mathf.Min(time, (float)Values[1 + index * 2 + 2]);
|
||||
}
|
||||
return time;
|
||||
}
|
||||
|
||||
private void SetStopTime(int index, float time)
|
||||
{
|
||||
time = ClampStopTime(index, time);
|
||||
SetValue(1 + index * 2, time);
|
||||
}
|
||||
|
||||
@@ -425,7 +395,7 @@ namespace FlaxEditor.Surface.Archetypes
|
||||
{
|
||||
var stop = _stops[i];
|
||||
var time = (float)Values[i * 2 + 1];
|
||||
stop.UpdateLocation(time);
|
||||
stop.Location = _gradient.BottomLeft + new Float2(time * _gradient.Width - stop.Width * 0.5f, 0.0f);
|
||||
stop.Color = (Color)Values[i * 2 + 2];
|
||||
stop.TooltipText = stop.Color + " at " + time;
|
||||
}
|
||||
|
||||
@@ -24,7 +24,6 @@ namespace FlaxEditor.Surface
|
||||
public BehaviorTreeSurface(IVisjectSurfaceOwner owner, Action onSave, FlaxEditor.Undo undo)
|
||||
: base(owner, onSave, undo, CreateStyle())
|
||||
{
|
||||
ScriptsBuilder.ScriptsReloadBegin += OnScriptsReloadBegin;
|
||||
}
|
||||
|
||||
private static SurfaceStyle CreateStyle()
|
||||
@@ -36,11 +35,6 @@ namespace FlaxEditor.Surface
|
||||
return style;
|
||||
}
|
||||
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
_nodesCache.Clear();
|
||||
}
|
||||
|
||||
private static void DrawBox(Box box)
|
||||
{
|
||||
var rect = new Rectangle(Float2.Zero, box.Size);
|
||||
@@ -192,7 +186,6 @@ namespace FlaxEditor.Surface
|
||||
{
|
||||
if (IsDisposing)
|
||||
return;
|
||||
ScriptsBuilder.ScriptsReloadBegin -= OnScriptsReloadBegin;
|
||||
_nodesCache.Wait();
|
||||
|
||||
base.OnDestroy();
|
||||
|
||||
@@ -415,15 +415,6 @@ namespace FlaxEditor.Surface
|
||||
// Init drag handlers
|
||||
DragHandlers.Add(_dragAssets = new DragAssets<DragDropEventArgs>(ValidateDragItem));
|
||||
DragHandlers.Add(_dragParameters = new DragNames<DragDropEventArgs>(SurfaceParameter.DragPrefix, ValidateDragParameter));
|
||||
|
||||
ScriptsBuilder.ScriptsReloadBegin += OnScriptsReloadBegin;
|
||||
}
|
||||
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
_activeVisjectCM = null;
|
||||
_cmPrimaryMenu?.Dispose();
|
||||
_cmPrimaryMenu = null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -1032,8 +1023,6 @@ namespace FlaxEditor.Surface
|
||||
_activeVisjectCM = null;
|
||||
_cmPrimaryMenu?.Dispose();
|
||||
|
||||
ScriptsBuilder.ScriptsReloadBegin -= OnScriptsReloadBegin;
|
||||
|
||||
base.OnDestroy();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -62,12 +62,6 @@ namespace FlaxEditor.Surface
|
||||
{
|
||||
_supportsImplicitCastFromObjectToBoolean = true;
|
||||
DragHandlers.Add(_dragActors = new DragActors(ValidateDragActor));
|
||||
ScriptsBuilder.ScriptsReloadBegin += OnScriptsReloadBegin;
|
||||
}
|
||||
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
_nodesCache.Clear();
|
||||
}
|
||||
|
||||
private bool ValidateDragActor(ActorNode actor)
|
||||
@@ -637,7 +631,6 @@ namespace FlaxEditor.Surface
|
||||
{
|
||||
if (IsDisposing)
|
||||
return;
|
||||
ScriptsBuilder.ScriptsReloadBegin -= OnScriptsReloadBegin;
|
||||
_nodesCache.Wait();
|
||||
|
||||
base.OnDestroy();
|
||||
|
||||
@@ -23,7 +23,7 @@ namespace FlaxEditor.Actions
|
||||
public Guid PrefabID;
|
||||
public Guid PrefabObjectID;
|
||||
|
||||
public Item(SceneObject obj, List<Item> nestedPrefabLinks)
|
||||
public unsafe Item(SceneObject obj, List<Item> nestedPrefabLinks)
|
||||
{
|
||||
ID = obj.ID;
|
||||
PrefabID = obj.PrefabID;
|
||||
@@ -33,7 +33,8 @@ namespace FlaxEditor.Actions
|
||||
// Check if this object comes from another nested prefab (to break link only from the top-level prefab)
|
||||
Item nested;
|
||||
nested.ID = ID;
|
||||
Editor.GetPrefabNestedObject(ref PrefabID, ref PrefabObjectID, out nested.PrefabID, out nested.PrefabObjectID);
|
||||
fixed (Item* i = &this)
|
||||
Editor.Internal_GetPrefabNestedObject(new IntPtr(&i->PrefabID), new IntPtr(&i->PrefabObjectID), new IntPtr(&nested.PrefabID), new IntPtr(&nested.PrefabObjectID));
|
||||
if (nested.PrefabID != Guid.Empty && nested.PrefabObjectID != Guid.Empty)
|
||||
nestedPrefabLinks.Add(nested);
|
||||
}
|
||||
|
||||
@@ -42,7 +42,7 @@ namespace FlaxEditor
|
||||
/// </summary>
|
||||
/// <typeparam name="TData">The type of the data. Must have <see cref="SerializableAttribute"/>.</typeparam>
|
||||
/// <seealso cref="FlaxEditor.IUndoAction" />
|
||||
[Serializable, HideInEditor]
|
||||
[Serializable]
|
||||
public abstract class UndoActionBase<TData> : IUndoAction where TData : struct
|
||||
{
|
||||
/// <summary>
|
||||
|
||||
@@ -5,7 +5,7 @@ namespace FlaxEditor.Utilities;
|
||||
/// <summary>
|
||||
/// Units display utilities for Editor.
|
||||
/// </summary>
|
||||
public static class Units
|
||||
public class Units
|
||||
{
|
||||
/// <summary>
|
||||
/// Factor of units per meter.
|
||||
|
||||
@@ -236,19 +236,19 @@ namespace FlaxEditor.Utilities
|
||||
/// <summary>
|
||||
/// The time/value axes tick steps for editors with timeline.
|
||||
/// </summary>
|
||||
internal static readonly double[] CurveTickSteps =
|
||||
internal static readonly float[] CurveTickSteps =
|
||||
{
|
||||
0.0000001, 0.0000005, 0.000001, 0.000005, 0.00001,
|
||||
0.00005, 0.0001, 0.0005, 0.001, 0.005,
|
||||
0.01, 0.05, 0.1, 0.5, 1,
|
||||
0.0000001f, 0.0000005f, 0.000001f, 0.000005f, 0.00001f,
|
||||
0.00005f, 0.0001f, 0.0005f, 0.001f, 0.005f,
|
||||
0.01f, 0.05f, 0.1f, 0.5f, 1,
|
||||
5, 10, 50, 100, 500,
|
||||
1000, 5000, 10000, 50000, 100000,
|
||||
500000, 1000000, 5000000, 10000000, 100000000
|
||||
};
|
||||
|
||||
internal delegate void DrawCurveTick(decimal tick, double step, float strength);
|
||||
internal delegate void DrawCurveTick(float tick, float strength);
|
||||
|
||||
internal static Int2 DrawCurveTicks(DrawCurveTick drawTick, double[] tickSteps, ref float[] tickStrengths, float min, float max, float pixelRange, float minDistanceBetweenTicks = 20, float maxDistanceBetweenTicks = 60)
|
||||
internal static Int2 DrawCurveTicks(DrawCurveTick drawTick, float[] tickSteps, ref float[] tickStrengths, float min, float max, float pixelRange, float minDistanceBetweenTicks = 20, float maxDistanceBetweenTicks = 60)
|
||||
{
|
||||
if (pixelRange <= Mathf.Epsilon || maxDistanceBetweenTicks <= minDistanceBetweenTicks)
|
||||
return Int2.Zero;
|
||||
@@ -262,10 +262,10 @@ namespace FlaxEditor.Utilities
|
||||
for (int i = tickSteps.Length - 1; i >= 0; i--)
|
||||
{
|
||||
// Calculate how far apart these modulo tick steps are spaced
|
||||
var tickSpacing = tickSteps[i] * pixelsInRange;
|
||||
float tickSpacing = tickSteps[i] * pixelsInRange;
|
||||
|
||||
// Calculate the strength of the tick markers based on the spacing
|
||||
tickStrengths[i] = (float)Mathd.Saturate((tickSpacing - minDistanceBetweenTicks) / (maxDistanceBetweenTicks - minDistanceBetweenTicks));
|
||||
tickStrengths[i] = Mathf.Saturate((tickSpacing - minDistanceBetweenTicks) / (maxDistanceBetweenTicks - minDistanceBetweenTicks));
|
||||
|
||||
// Beyond threshold the ticks don't get any bigger or fatter
|
||||
if (tickStrengths[i] >= 1)
|
||||
@@ -283,7 +283,7 @@ namespace FlaxEditor.Utilities
|
||||
// Draw all tick levels
|
||||
for (int level = 0; level < tickLevels; level++)
|
||||
{
|
||||
var strength = tickStrengths[smallestTick + level];
|
||||
float strength = tickStrengths[smallestTick + level];
|
||||
if (strength <= Mathf.Epsilon)
|
||||
continue;
|
||||
|
||||
@@ -291,36 +291,20 @@ namespace FlaxEditor.Utilities
|
||||
int l = Mathf.Clamp(smallestTick + level, 0, tickSteps.Length - 2);
|
||||
var lStep = tickSteps[l];
|
||||
var lNextStep = tickSteps[l + 1];
|
||||
var startTick = Mathd.FloorToInt(min / lStep);
|
||||
var endTick = Mathd.CeilToInt(max / lStep);
|
||||
for (var i = startTick; i <= endTick; i++)
|
||||
int startTick = Mathf.FloorToInt(min / lStep);
|
||||
int endTick = Mathf.CeilToInt(max / lStep);
|
||||
for (int i = startTick; i <= endTick; i++)
|
||||
{
|
||||
if (l < biggestTick && (i % Mathd.RoundToInt(lNextStep / lStep) == 0))
|
||||
if (l < biggestTick && (i % Mathf.RoundToInt(lNextStep / lStep) == 0))
|
||||
continue;
|
||||
var tick = (decimal)lStep * i;
|
||||
drawTick(tick, lStep, strength);
|
||||
var tick = i * lStep;
|
||||
drawTick(tick, strength);
|
||||
}
|
||||
}
|
||||
|
||||
return new Int2(smallestTick, biggestTick);
|
||||
}
|
||||
|
||||
internal static float GetCurveGridSnap(double[] tickSteps, ref float[] tickStrengths, float min, float max, float pixelRange, float minDistanceBetweenTicks = 20, float maxDistanceBetweenTicks = 60)
|
||||
{
|
||||
double gridStep = 0; // No grid
|
||||
float gridWeight = 0.0f;
|
||||
DrawCurveTicks((decimal tick, double step, float strength) =>
|
||||
{
|
||||
// Find the smallest grid step that has meaningful strength (it's the most visible to the user)
|
||||
if (strength > gridWeight && (step < gridStep || gridStep <= 0.0) && strength > 0.5f)
|
||||
{
|
||||
gridStep = Math.Abs(step);
|
||||
gridWeight = strength;
|
||||
}
|
||||
}, tickSteps, ref tickStrengths, min, max, pixelRange, minDistanceBetweenTicks, maxDistanceBetweenTicks);
|
||||
return (float)gridStep;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determines whether the specified path string contains any invalid character.
|
||||
/// </summary>
|
||||
@@ -1544,12 +1528,5 @@ namespace FlaxEditor.Utilities
|
||||
}
|
||||
return path;
|
||||
}
|
||||
|
||||
internal static ISceneContextWindow GetSceneContext(this Control c)
|
||||
{
|
||||
while (c != null && !(c is ISceneContextWindow))
|
||||
c = c.Parent;
|
||||
return c as ISceneContextWindow;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,12 +5,10 @@ using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using FlaxEditor.Content;
|
||||
using FlaxEditor.Gizmo;
|
||||
using FlaxEditor.GUI.ContextMenu;
|
||||
using FlaxEditor.SceneGraph;
|
||||
using FlaxEditor.Scripting;
|
||||
using FlaxEditor.Viewport.Cameras;
|
||||
using FlaxEditor.Viewport.Previews;
|
||||
using FlaxEditor.Viewport.Widgets;
|
||||
using FlaxEditor.Windows.Assets;
|
||||
using FlaxEngine;
|
||||
using FlaxEngine.GUI;
|
||||
@@ -46,7 +44,7 @@ namespace FlaxEditor.Viewport
|
||||
private sealed class PrefabUIEditorRoot : UIEditorRoot
|
||||
{
|
||||
private readonly PrefabWindowViewport _viewport;
|
||||
private bool UI => _viewport.ShowUI;
|
||||
private bool UI => _viewport._hasUILinkedCached;
|
||||
|
||||
public PrefabUIEditorRoot(PrefabWindowViewport viewport)
|
||||
: base(true)
|
||||
@@ -69,78 +67,8 @@ namespace FlaxEditor.Viewport
|
||||
private PrefabSpritesRenderer _spritesRenderer;
|
||||
private IntPtr _tempDebugDrawContext;
|
||||
|
||||
private bool _hasUILinkedCached;
|
||||
private PrefabUIEditorRoot _uiRoot;
|
||||
private bool _showUI = false;
|
||||
|
||||
private ContextMenuButton _uiModeButton;
|
||||
|
||||
/// <summary>
|
||||
/// Event fired when the UI Mode is toggled.
|
||||
/// </summary>
|
||||
public event Action<bool> UIModeToggled;
|
||||
|
||||
/// <summary>
|
||||
/// set the initial UI mod
|
||||
/// </summary>
|
||||
/// <param name="value">the initial ShowUI value</param>
|
||||
public void SetInitialUIMode(bool value)
|
||||
{
|
||||
ShowUI = value;
|
||||
_uiModeButton.Checked = value;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Whether to show the UI mode or not.
|
||||
/// </summary>
|
||||
public bool ShowUI
|
||||
{
|
||||
get => _showUI;
|
||||
set
|
||||
{
|
||||
_showUI = value;
|
||||
if (_showUI)
|
||||
{
|
||||
// UI widget
|
||||
Gizmos.Active = null;
|
||||
ViewportCamera = new UIEditorCamera { UIEditor = _uiRoot };
|
||||
|
||||
// Hide 3D visuals
|
||||
ShowEditorPrimitives = false;
|
||||
ShowDefaultSceneActors = false;
|
||||
ShowDebugDraw = false;
|
||||
|
||||
// Show whole UI on startup
|
||||
var canvas = (CanvasRootControl)_uiParentLink.Children.FirstOrDefault(x => x is CanvasRootControl);
|
||||
if (canvas != null)
|
||||
ViewportCamera.ShowActor(canvas.Canvas);
|
||||
else if (Instance is UIControl)
|
||||
ViewportCamera.ShowActor(Instance);
|
||||
_uiRoot.Visible = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Generic prefab
|
||||
Gizmos.Active = TransformGizmo;
|
||||
ViewportCamera = new FPSCamera();
|
||||
_uiRoot.Visible = false;
|
||||
}
|
||||
|
||||
// Update default components usage
|
||||
bool defaultFeatures = !_showUI;
|
||||
_disableInputUpdate = _showUI;
|
||||
_spritesRenderer.Enabled = defaultFeatures;
|
||||
SelectionOutline.Enabled = defaultFeatures;
|
||||
_showDefaultSceneButton.Visible = defaultFeatures;
|
||||
_cameraWidget.Visible = defaultFeatures;
|
||||
_cameraButton.Visible = defaultFeatures;
|
||||
_orthographicModeButton.Visible = defaultFeatures;
|
||||
Task.Enabled = defaultFeatures;
|
||||
UseAutomaticTaskManagement = defaultFeatures;
|
||||
ShowDefaultSceneActors = defaultFeatures;
|
||||
TintColor = defaultFeatures ? Color.White : Color.Transparent;
|
||||
UIModeToggled?.Invoke(_showUI);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Drag and drop handlers
|
||||
@@ -210,11 +138,6 @@ namespace FlaxEditor.Viewport
|
||||
_uiRoot.IndexInParent = 0; // Move viewport down below other widgets in the viewport
|
||||
_uiParentLink = _uiRoot.UIRoot;
|
||||
|
||||
// UI mode buton
|
||||
_uiModeButton = ViewWidgetShowMenu.AddButton("UI Mode", (button) => ShowUI = button.Checked);
|
||||
_uiModeButton.AutoCheck = true;
|
||||
_uiModeButton.VisibleChanged += control => (control as ContextMenuButton).Checked = ShowUI;
|
||||
|
||||
EditorGizmoViewport.AddGizmoViewportWidgets(this, TransformGizmo);
|
||||
|
||||
// Setup input actions
|
||||
@@ -223,8 +146,58 @@ namespace FlaxEditor.Viewport
|
||||
SetUpdate(ref _update, OnUpdate);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Updates the viewport's gizmos, especially to toggle between 3D and UI editing modes.
|
||||
/// </summary>
|
||||
internal void UpdateGizmoMode()
|
||||
{
|
||||
// Skip if gizmo mode was unmodified
|
||||
if (_hasUILinked == _hasUILinkedCached)
|
||||
return;
|
||||
_hasUILinkedCached = _hasUILinked;
|
||||
|
||||
if (_hasUILinked)
|
||||
{
|
||||
// UI widget
|
||||
Gizmos.Active = null;
|
||||
ViewportCamera = new UIEditorCamera { UIEditor = _uiRoot };
|
||||
|
||||
// Hide 3D visuals
|
||||
ShowEditorPrimitives = false;
|
||||
ShowDefaultSceneActors = false;
|
||||
ShowDebugDraw = false;
|
||||
|
||||
// Show whole UI on startup
|
||||
var canvas = (CanvasRootControl)_uiParentLink.Children.FirstOrDefault(x => x is CanvasRootControl);
|
||||
if (canvas != null)
|
||||
ViewportCamera.ShowActor(canvas.Canvas);
|
||||
else if (Instance is UIControl)
|
||||
ViewportCamera.ShowActor(Instance);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Generic prefab
|
||||
Gizmos.Active = TransformGizmo;
|
||||
ViewportCamera = new FPSCamera();
|
||||
}
|
||||
|
||||
// Update default components usage
|
||||
bool defaultFeatures = !_hasUILinked;
|
||||
_disableInputUpdate = _hasUILinked;
|
||||
_spritesRenderer.Enabled = defaultFeatures;
|
||||
SelectionOutline.Enabled = defaultFeatures;
|
||||
_showDefaultSceneButton.Visible = defaultFeatures;
|
||||
_cameraWidget.Visible = defaultFeatures;
|
||||
_cameraButton.Visible = defaultFeatures;
|
||||
_orthographicModeButton.Visible = defaultFeatures;
|
||||
Task.Enabled = defaultFeatures;
|
||||
UseAutomaticTaskManagement = defaultFeatures;
|
||||
TintColor = defaultFeatures ? Color.White : Color.Transparent;
|
||||
}
|
||||
|
||||
private void OnUpdate(float deltaTime)
|
||||
{
|
||||
UpdateGizmoMode();
|
||||
for (int i = 0; i < Gizmos.Count; i++)
|
||||
{
|
||||
Gizmos[i].Update(deltaTime);
|
||||
|
||||
@@ -58,8 +58,6 @@ namespace FlaxEditor.Windows.Assets
|
||||
InputActions.Add(options => options.Save, Save);
|
||||
|
||||
UpdateTitle();
|
||||
|
||||
ScriptsBuilder.ScriptsReloadBegin += OnScriptsReloadBegin;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -153,8 +151,6 @@ namespace FlaxEditor.Windows.Assets
|
||||
/// <inheritdoc />
|
||||
public override void OnDestroy()
|
||||
{
|
||||
ScriptsBuilder.ScriptsReloadBegin -= OnScriptsReloadBegin;
|
||||
|
||||
if (_item != null)
|
||||
{
|
||||
// Ensure to remove linkage to the item
|
||||
@@ -164,15 +160,6 @@ namespace FlaxEditor.Windows.Assets
|
||||
base.OnDestroy();
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected virtual void OnScriptsReloadBegin()
|
||||
{
|
||||
if (!IsHidden)
|
||||
{
|
||||
Editor.Instance.Windows.AddToRestore(this);
|
||||
}
|
||||
}
|
||||
|
||||
#region IEditable Implementation
|
||||
|
||||
private bool _isEdited;
|
||||
|
||||
@@ -268,11 +268,8 @@ namespace FlaxEditor.Windows.Assets
|
||||
UpdateKnowledge();
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void OnScriptsReloadBegin()
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
base.OnScriptsReloadBegin();
|
||||
|
||||
// TODO: impl hot-reload for BT to nicely refresh state (save asset, clear undo/properties, reload surface)
|
||||
Close();
|
||||
}
|
||||
|
||||
@@ -200,7 +200,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
ViewportCamera = new FPSCamera(),
|
||||
Parent = _split.Panel1
|
||||
};
|
||||
_preview.Task.ViewFlags &= ~ViewFlags.Sky & ~ViewFlags.Bloom & ~ViewFlags.EyeAdaptation;
|
||||
_preview.Task.ViewFlags &= ~ViewFlags.Sky & ~ViewFlags.Bloom;
|
||||
|
||||
// Asset properties
|
||||
_propertiesPresenter = new CustomEditorPresenter(null);
|
||||
|
||||
@@ -124,10 +124,8 @@ namespace FlaxEditor.Windows.Assets
|
||||
UpdateToolstrip();
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void OnScriptsReloadBegin()
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
base.OnScriptsReloadBegin();
|
||||
Close();
|
||||
}
|
||||
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using FlaxEditor.Content;
|
||||
using FlaxEditor.GUI.ContextMenu;
|
||||
using FlaxEditor.GUI.Drag;
|
||||
@@ -85,7 +86,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
{
|
||||
return Editor.Instance.CodeEditing.Actors.Get().Contains(actorType);
|
||||
}
|
||||
|
||||
|
||||
private static bool ValidateDragControlType(ScriptType controlType)
|
||||
{
|
||||
return Editor.Instance.CodeEditing.Controls.Get().Contains(controlType);
|
||||
@@ -170,8 +171,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
var actor = item.OnEditorDrop(this);
|
||||
actor.Name = item.ShortName;
|
||||
_window.Spawn(actor);
|
||||
var graphNode = _window.Graph.Root.Find(actor);
|
||||
;
|
||||
var graphNode = _window.Graph.Root.Find(actor);;
|
||||
if (graphNode != null)
|
||||
graphNodes.Add(graphNode);
|
||||
}
|
||||
@@ -235,8 +235,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
}
|
||||
actor.Name = actorType.Name;
|
||||
_window.Spawn(actor);
|
||||
var graphNode = _window.Graph.Root.Find(actor);
|
||||
;
|
||||
var graphNode = _window.Graph.Root.Find(actor);;
|
||||
if (graphNode != null)
|
||||
graphNodes.Add(graphNode);
|
||||
}
|
||||
@@ -291,7 +290,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
|
||||
// Basic editing options
|
||||
|
||||
var b = contextMenu.AddButton("Rename", RenameSelection);
|
||||
var b = contextMenu.AddButton("Rename", Rename);
|
||||
b.Enabled = isSingleActorSelected;
|
||||
|
||||
b = contextMenu.AddButton("Duplicate", Duplicate);
|
||||
@@ -415,8 +414,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
contextMenu.Show(parent, location);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public void RenameSelection()
|
||||
private void Rename()
|
||||
{
|
||||
var selection = Selection;
|
||||
if (selection.Count != 0 && selection[0] is ActorNode actor)
|
||||
@@ -427,12 +425,6 @@ namespace FlaxEditor.Windows.Assets
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public void FocusSelection()
|
||||
{
|
||||
_viewport.FocusSelection();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Spawns the specified actor to the prefab (adds actor to root).
|
||||
/// </summary>
|
||||
@@ -476,7 +468,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
|
||||
// Spawn it
|
||||
Spawn(actor);
|
||||
RenameSelection();
|
||||
Rename();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -19,7 +19,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
/// </summary>
|
||||
/// <seealso cref="Prefab" />
|
||||
/// <seealso cref="FlaxEditor.Windows.Assets.AssetEditorWindow" />
|
||||
public sealed partial class PrefabWindow : AssetEditorWindowBase<Prefab>, IPresenterOwner, ISceneContextWindow
|
||||
public sealed partial class PrefabWindow : AssetEditorWindowBase<Prefab>, IPresenterOwner
|
||||
{
|
||||
private readonly SplitPanel _split1;
|
||||
private readonly SplitPanel _split2;
|
||||
@@ -194,6 +194,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
|
||||
Editor.Prefabs.PrefabApplied += OnPrefabApplied;
|
||||
ScriptsBuilder.ScriptsReloadBegin += OnScriptsReloadBegin;
|
||||
ScriptsBuilder.ScriptsReloadEnd += OnScriptsReloadEnd;
|
||||
|
||||
// Setup input actions
|
||||
InputActions.Add(options => options.Undo, () =>
|
||||
@@ -211,8 +212,8 @@ namespace FlaxEditor.Windows.Assets
|
||||
InputActions.Add(options => options.Paste, Paste);
|
||||
InputActions.Add(options => options.Duplicate, Duplicate);
|
||||
InputActions.Add(options => options.Delete, Delete);
|
||||
InputActions.Add(options => options.Rename, RenameSelection);
|
||||
InputActions.Add(options => options.FocusSelection, FocusSelection);
|
||||
InputActions.Add(options => options.Rename, Rename);
|
||||
InputActions.Add(options => options.FocusSelection, _viewport.FocusSelection);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -286,10 +287,8 @@ namespace FlaxEditor.Windows.Assets
|
||||
return false;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void OnScriptsReloadBegin()
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
base.OnScriptsReloadBegin();
|
||||
_isScriptsReloading = true;
|
||||
|
||||
if (_asset == null || !_asset.IsLoaded)
|
||||
@@ -317,8 +316,19 @@ namespace FlaxEditor.Windows.Assets
|
||||
Graph.MainActor = null;
|
||||
_viewport.Prefab = null;
|
||||
_undo?.Clear(); // TODO: maybe don't clear undo?
|
||||
}
|
||||
|
||||
Close();
|
||||
private void OnScriptsReloadEnd()
|
||||
{
|
||||
_isScriptsReloading = false;
|
||||
|
||||
if (_asset == null || !_asset.IsLoaded)
|
||||
return;
|
||||
|
||||
// Restore
|
||||
OnPrefabOpened();
|
||||
_undo.Clear();
|
||||
ClearEditedFlag();
|
||||
}
|
||||
|
||||
private void OnUndoEvent(IUndoAction action)
|
||||
@@ -345,22 +355,13 @@ namespace FlaxEditor.Windows.Assets
|
||||
private void OnPrefabOpened()
|
||||
{
|
||||
_viewport.Prefab = _asset;
|
||||
if (Editor.ProjectCache.TryGetCustomData($"UIMode:{_asset.ID}", out bool value))
|
||||
_viewport.SetInitialUIMode(value);
|
||||
else
|
||||
_viewport.SetInitialUIMode(_viewport._hasUILinked);
|
||||
_viewport.UIModeToggled += OnUIModeToggled;
|
||||
_viewport.UpdateGizmoMode();
|
||||
Graph.MainActor = _viewport.Instance;
|
||||
Selection.Clear();
|
||||
Select(Graph.Main);
|
||||
Graph.Root.TreeNode.Expand(true);
|
||||
}
|
||||
|
||||
private void OnUIModeToggled(bool value)
|
||||
{
|
||||
Editor.ProjectCache.SetCustomData($"UIMode:{_asset.ID}", value);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void Save()
|
||||
{
|
||||
@@ -537,6 +538,7 @@ namespace FlaxEditor.Windows.Assets
|
||||
{
|
||||
Editor.Prefabs.PrefabApplied -= OnPrefabApplied;
|
||||
ScriptsBuilder.ScriptsReloadBegin -= OnScriptsReloadBegin;
|
||||
ScriptsBuilder.ScriptsReloadEnd -= OnScriptsReloadEnd;
|
||||
|
||||
_undo.Dispose();
|
||||
Graph.Dispose();
|
||||
|
||||
@@ -29,7 +29,6 @@ namespace FlaxEditor.Windows
|
||||
private const string ProjectDataLastViewedFolder = "LastViewedFolder";
|
||||
private bool _isWorkspaceDirty;
|
||||
private string _workspaceRebuildLocation;
|
||||
private string _lastViewedFolderBeforeReload;
|
||||
private SplitPanel _split;
|
||||
private Panel _contentViewPanel;
|
||||
private Panel _contentTreePanel;
|
||||
@@ -145,6 +144,26 @@ namespace FlaxEditor.Windows
|
||||
|
||||
FlaxEditor.Utilities.Utils.SetupCommonInputActions(this);
|
||||
|
||||
// Content database events
|
||||
editor.ContentDatabase.WorkspaceModified += () => _isWorkspaceDirty = true;
|
||||
editor.ContentDatabase.ItemRemoved += OnContentDatabaseItemRemoved;
|
||||
editor.ContentDatabase.WorkspaceRebuilding += () => { _workspaceRebuildLocation = SelectedNode?.Path; };
|
||||
editor.ContentDatabase.WorkspaceRebuilt += () =>
|
||||
{
|
||||
var selected = Editor.ContentDatabase.Find(_workspaceRebuildLocation);
|
||||
if (selected is ContentFolder selectedFolder)
|
||||
{
|
||||
_navigationUnlocked = false;
|
||||
RefreshView(selectedFolder.Node);
|
||||
_tree.Select(selectedFolder.Node);
|
||||
UpdateItemsSearch();
|
||||
_navigationUnlocked = true;
|
||||
UpdateUI();
|
||||
}
|
||||
else
|
||||
ShowRoot();
|
||||
};
|
||||
|
||||
var options = Editor.Options;
|
||||
options.OptionsChanged += OnOptionsChanged;
|
||||
|
||||
@@ -1017,61 +1036,6 @@ namespace FlaxEditor.Windows
|
||||
|
||||
/// <inheritdoc />
|
||||
public override void OnInit()
|
||||
{
|
||||
// Content database events
|
||||
Editor.ContentDatabase.WorkspaceModified += () => _isWorkspaceDirty = true;
|
||||
Editor.ContentDatabase.ItemRemoved += OnContentDatabaseItemRemoved;
|
||||
Editor.ContentDatabase.WorkspaceRebuilding += () => { _workspaceRebuildLocation = SelectedNode?.Path; };
|
||||
Editor.ContentDatabase.WorkspaceRebuilt += () =>
|
||||
{
|
||||
var selected = Editor.ContentDatabase.Find(_workspaceRebuildLocation);
|
||||
if (selected is ContentFolder selectedFolder)
|
||||
{
|
||||
_navigationUnlocked = false;
|
||||
RefreshView(selectedFolder.Node);
|
||||
_tree.Select(selectedFolder.Node);
|
||||
UpdateItemsSearch();
|
||||
_navigationUnlocked = true;
|
||||
UpdateUI();
|
||||
}
|
||||
else if (_root != null)
|
||||
ShowRoot();
|
||||
};
|
||||
|
||||
Refresh();
|
||||
|
||||
// Load last viewed folder
|
||||
if (Editor.ProjectCache.TryGetCustomData(ProjectDataLastViewedFolder, out string lastViewedFolder))
|
||||
{
|
||||
if (Editor.ContentDatabase.Find(lastViewedFolder) is ContentFolder folder)
|
||||
_tree.Select(folder.Node);
|
||||
}
|
||||
|
||||
ScriptsBuilder.ScriptsReloadBegin += OnScriptsReloadBegin;
|
||||
ScriptsBuilder.ScriptsReloadEnd += OnScriptsReloadEnd;
|
||||
}
|
||||
|
||||
private void OnScriptsReloadBegin()
|
||||
{
|
||||
var lastViewedFolder = _tree.Selection.Count == 1 ? _tree.SelectedNode as ContentTreeNode : null;
|
||||
_lastViewedFolderBeforeReload = lastViewedFolder?.Path ?? string.Empty;
|
||||
|
||||
_tree.RemoveChild(_root);
|
||||
_root = null;
|
||||
}
|
||||
|
||||
private void OnScriptsReloadEnd()
|
||||
{
|
||||
Refresh();
|
||||
|
||||
if (!string.IsNullOrEmpty(_lastViewedFolderBeforeReload))
|
||||
{
|
||||
if (Editor.ContentDatabase.Find(_lastViewedFolderBeforeReload) is ContentFolder folder)
|
||||
_tree.Select(folder.Node);
|
||||
}
|
||||
}
|
||||
|
||||
private void Refresh()
|
||||
{
|
||||
// Setup content root node
|
||||
_root = new RootContentTreeNode
|
||||
@@ -1108,6 +1072,13 @@ namespace FlaxEditor.Windows
|
||||
// Update UI layout
|
||||
_isLayoutLocked = false;
|
||||
PerformLayout();
|
||||
|
||||
// Load last viewed folder
|
||||
if (Editor.ProjectCache.TryGetCustomData(ProjectDataLastViewedFolder, out string lastViewedFolder))
|
||||
{
|
||||
if (Editor.ContentDatabase.Find(lastViewedFolder) is ContentFolder folder)
|
||||
_tree.Select(folder.Node);
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
@@ -1255,8 +1226,6 @@ namespace FlaxEditor.Windows
|
||||
_viewDropdown = null;
|
||||
|
||||
Editor.Options.OptionsChanged -= OnOptionsChanged;
|
||||
ScriptsBuilder.ScriptsReloadBegin -= OnScriptsReloadBegin;
|
||||
ScriptsBuilder.ScriptsReloadEnd -= OnScriptsReloadEnd;
|
||||
|
||||
base.OnDestroy();
|
||||
}
|
||||
|
||||
@@ -95,15 +95,15 @@ namespace FlaxEditor.Windows
|
||||
{
|
||||
case LogType.Warning:
|
||||
Group = LogGroup.Warning;
|
||||
Icon = _window._iconWarning;
|
||||
Icon = _window.IconWarning;
|
||||
break;
|
||||
case LogType.Info:
|
||||
Group = LogGroup.Info;
|
||||
Icon = _window._iconInfo;
|
||||
Icon = _window.IconInfo;
|
||||
break;
|
||||
default:
|
||||
Group = LogGroup.Error;
|
||||
Icon = _window._iconError;
|
||||
Icon = _window.IconError;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -131,21 +131,20 @@ namespace FlaxEditor.Windows
|
||||
else if (index % 2 == 0)
|
||||
Render2D.FillRectangle(clientRect, style.Background * 0.9f);
|
||||
|
||||
var color = Group == LogGroup.Error ? _window._colorError : (Group == LogGroup.Warning ? _window._colorWarning : _window._colorInfo);
|
||||
|
||||
// Icon
|
||||
Render2D.DrawSprite(Icon, new Rectangle(5, 0, 32, 32), color);
|
||||
var iconColor = Group == LogGroup.Error ? Color.Red : (Group == LogGroup.Warning ? Color.Yellow : style.Foreground);
|
||||
Render2D.DrawSprite(Icon, new Rectangle(5, 0, 32, 32), iconColor);
|
||||
|
||||
// Title
|
||||
var textRect = new Rectangle(38, 2, clientRect.Width - 40, clientRect.Height - 10);
|
||||
Render2D.PushClip(ref clientRect);
|
||||
if (LogCount == 1)
|
||||
{
|
||||
Render2D.DrawText(style.FontMedium, Desc.Title, textRect, color);
|
||||
Render2D.DrawText(style.FontMedium, Desc.Title, textRect, style.Foreground);
|
||||
}
|
||||
else if (LogCount > 1)
|
||||
{
|
||||
Render2D.DrawText(style.FontMedium, $"{Desc.Title} ({LogCount})", textRect, color);
|
||||
Render2D.DrawText(style.FontMedium, $"{Desc.Title} ({LogCount})", textRect, style.Foreground);
|
||||
}
|
||||
Render2D.PopClip();
|
||||
}
|
||||
@@ -305,12 +304,10 @@ namespace FlaxEditor.Windows
|
||||
private readonly ToolStripButton[] _groupButtons = new ToolStripButton[3];
|
||||
|
||||
private LogType _iconType = LogType.Info;
|
||||
private SpriteHandle _iconInfo;
|
||||
private SpriteHandle _iconWarning;
|
||||
private SpriteHandle _iconError;
|
||||
private Color _colorInfo;
|
||||
private Color _colorWarning;
|
||||
private Color _colorError;
|
||||
|
||||
internal SpriteHandle IconInfo;
|
||||
internal SpriteHandle IconWarning;
|
||||
internal SpriteHandle IconError;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="DebugLogWindow"/> class.
|
||||
@@ -320,7 +317,7 @@ namespace FlaxEditor.Windows
|
||||
: base(editor, true, ScrollBars.None)
|
||||
{
|
||||
Title = "Debug Log";
|
||||
Icon = _iconInfo;
|
||||
Icon = IconInfo;
|
||||
FlaxEditor.Utilities.Utils.SetupCommonInputActions(this);
|
||||
|
||||
// Toolstrip
|
||||
@@ -364,6 +361,7 @@ namespace FlaxEditor.Windows
|
||||
editor.Options.Apply(editor.Options.Options);
|
||||
}).SetAutoCheck(true).LinkTooltip("Shows/hides info messages");
|
||||
UpdateCount();
|
||||
OnEditorOptionsChanged(Editor.Options.Options);
|
||||
|
||||
// Split panel
|
||||
_split = new SplitPanel(Orientation.Vertical, ScrollBars.Vertical, ScrollBars.Both)
|
||||
@@ -396,17 +394,14 @@ namespace FlaxEditor.Windows
|
||||
};
|
||||
|
||||
// Cache entries icons
|
||||
_iconInfo = Editor.Icons.Info64;
|
||||
_iconWarning = Editor.Icons.Warning64;
|
||||
_iconError = Editor.Icons.Error64;
|
||||
IconInfo = Editor.Icons.Info64;
|
||||
IconWarning = Editor.Icons.Warning64;
|
||||
IconError = Editor.Icons.Error64;
|
||||
|
||||
// Bind events
|
||||
Editor.Options.OptionsChanged += OnEditorOptionsChanged;
|
||||
Debug.Logger.LogHandler.SendLog += LogHandlerOnSendLog;
|
||||
Debug.Logger.LogHandler.SendExceptionLog += LogHandlerOnSendExceptionLog;
|
||||
|
||||
// Init editor options
|
||||
OnEditorOptionsChanged(Editor.Options.Options);
|
||||
}
|
||||
|
||||
private void OnEditorOptionsChanged(EditorOptions options)
|
||||
@@ -418,9 +413,6 @@ namespace FlaxEditor.Windows
|
||||
_groupButtons[0].Checked = options.Interface.DebugLogShowErrorMessages;
|
||||
_groupButtons[1].Checked = options.Interface.DebugLogShowWarningMessages;
|
||||
_groupButtons[2].Checked = options.Interface.DebugLogShowInfoMessages;
|
||||
_colorInfo = options.Interface.OutputLogTextColor;
|
||||
_colorWarning = options.Interface.OutputLogWarningTextColor;
|
||||
_colorError = options.Interface.OutputLogErrorTextColor;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -430,6 +422,7 @@ namespace FlaxEditor.Windows
|
||||
{
|
||||
if (_entriesPanel == null)
|
||||
return;
|
||||
|
||||
RemoveEntries();
|
||||
}
|
||||
|
||||
|
||||
@@ -23,8 +23,6 @@ namespace FlaxEditor.Windows
|
||||
private readonly GameRoot _guiRoot;
|
||||
private bool _showGUI = true;
|
||||
private bool _showDebugDraw = false;
|
||||
private bool _audioMuted = false;
|
||||
private float _audioVolume = 1;
|
||||
private bool _isMaximized = false, _isUnlockingMouse = false;
|
||||
private bool _isFloating = false, _isBorderless = false;
|
||||
private bool _cursorVisible = true;
|
||||
@@ -93,35 +91,6 @@ namespace FlaxEditor.Windows
|
||||
set => _showDebugDraw = value;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or set a value indicating whether Audio is muted.
|
||||
/// </summary>
|
||||
public bool AudioMuted
|
||||
{
|
||||
get => _audioMuted;
|
||||
set
|
||||
{
|
||||
Audio.MasterVolume = value ? 0 : AudioVolume;
|
||||
_audioMuted = value;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a value that set the audio volume.
|
||||
/// </summary>
|
||||
public float AudioVolume
|
||||
{
|
||||
get => _audioVolume;
|
||||
set
|
||||
{
|
||||
if (!AudioMuted)
|
||||
Audio.MasterVolume = value;
|
||||
|
||||
_audioVolume = value;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a value indicating whether the game window is maximized (only in play mode).
|
||||
/// </summary>
|
||||
@@ -677,24 +646,6 @@ namespace FlaxEditor.Windows
|
||||
checkbox.StateChanged += x => ShowDebugDraw = x.Checked;
|
||||
}
|
||||
|
||||
menu.AddSeparator();
|
||||
|
||||
// Mute Audio
|
||||
{
|
||||
var button = menu.AddButton("Mute Audio");
|
||||
button.CloseMenuOnClick = false;
|
||||
var checkbox = new CheckBox(140, 2, AudioMuted) { Parent = button };
|
||||
checkbox.StateChanged += x => AudioMuted = x.Checked;
|
||||
}
|
||||
|
||||
// Audio Volume
|
||||
{
|
||||
var button = menu.AddButton("Audio Volume");
|
||||
button.CloseMenuOnClick = false;
|
||||
var slider = new FloatValueBox(AudioVolume, 140, 2, 50, 0, 1) { Parent = button };
|
||||
slider.ValueChanged += () => AudioVolume = slider.Value;
|
||||
}
|
||||
|
||||
menu.MinimumWidth = 200;
|
||||
menu.AddSeparator();
|
||||
}
|
||||
|
||||
@@ -286,9 +286,7 @@ namespace FlaxEditor.Windows
|
||||
_output.DefaultStyle.Font == options.Interface.OutputLogTextFont &&
|
||||
_output.DefaultStyle.Color == options.Interface.OutputLogTextColor &&
|
||||
_output.DefaultStyle.ShadowColor == options.Interface.OutputLogTextShadowColor &&
|
||||
_output.DefaultStyle.ShadowOffset == options.Interface.OutputLogTextShadowOffset &&
|
||||
_output.WarningStyle.Color == options.Interface.OutputLogWarningTextColor &&
|
||||
_output.ErrorStyle.Color == options.Interface.OutputLogErrorTextColor)
|
||||
_output.DefaultStyle.ShadowOffset == options.Interface.OutputLogTextShadowOffset)
|
||||
return;
|
||||
|
||||
_output.DefaultStyle = new TextBlockStyle
|
||||
@@ -299,11 +297,10 @@ namespace FlaxEditor.Windows
|
||||
ShadowOffset = options.Interface.OutputLogTextShadowOffset,
|
||||
BackgroundSelectedBrush = new SolidColorBrush(Style.Current.BackgroundSelected),
|
||||
};
|
||||
|
||||
_output.WarningStyle = _output.DefaultStyle;
|
||||
_output.WarningStyle.Color = options.Interface.OutputLogWarningTextColor;
|
||||
_output.WarningStyle.Color = Color.Yellow;
|
||||
_output.ErrorStyle = _output.DefaultStyle;
|
||||
_output.ErrorStyle.Color = options.Interface.OutputLogErrorTextColor;
|
||||
_output.ErrorStyle.Color = Color.Red;
|
||||
|
||||
_timestampsFormats = options.Interface.OutputLogTimestampsFormat;
|
||||
_showLogType = options.Interface.OutputLogShowLogType;
|
||||
@@ -604,7 +601,7 @@ namespace FlaxEditor.Windows
|
||||
var cachedScrollValue = _vScroll.Value;
|
||||
var cachedSelection = _output.SelectionRange;
|
||||
var cachedOutputTargetViewOffset = _output.TargetViewOffset;
|
||||
var isBottomScroll = _vScroll.Value >= _vScroll.Maximum - (_scrollSize * 2) || wasEmpty;
|
||||
var isBottomScroll = _vScroll.Value >= _vScroll.Maximum - (_scrollSize*2) || wasEmpty;
|
||||
_output.Text = _textBuffer.ToString();
|
||||
_output.TargetViewOffset = cachedOutputTargetViewOffset;
|
||||
_textBufferCount = _entries.Count;
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user