Bladeren bron

添加时间轴,按键和其他需要继续加入对应图片。

AncienWish 2 maanden geleden
bovenliggende
commit
9ed931821b

+ 1 - 1
Ability/Plugins/EzAbility/Source/EzAbilityEditor/EzAbilityEditor.Build.cs

@@ -1,4 +1,4 @@
-// Copyright Epic Games, Inc. All Rights Reserved.
+// Copyright Epic Games, Inc. All Rights Reserved.
 
 using UnrealBuildTool;
 

+ 12 - 1
Ability/Plugins/EzAbility/Source/EzAbilityEditor/Private/EzAbilityEditorApplicationMode.cpp

@@ -12,6 +12,8 @@
 #include "AdvancedPreviewScene.h"
 #include "PreviewScene.h"
 #include "Toolkits/AssetEditorToolkit.h"
+#include "Editor/AnimationEditor/Private/AnimationEditor.h"
+#include "EzAbilityTimelineSummoner.h"
 
 #define LOCTEXT_NAMESPACE "EzAbilityEditorApplicationModeh"
 
@@ -24,6 +26,8 @@ FEzAbilityEditorApplicationMode::FEzAbilityEditorApplicationMode(const TSharedRe
 	//FEzAbilityViewModule& AbilityViewModule = FModuleManager::LoadModuleChecked<FEzAbilityViewModule>("AbilityView");
 	PreviewScene = MakeShareable(new FAdvancedPreviewScene(FPreviewScene::ConstructionValues()));
 	EzAbilityEditorTabFactories.RegisterFactory(MakeShareable(new FEzAbilityViewPortSummoner(InHostingApp, PreviewScene.ToSharedRef())));
+	EzAbilityEditorTabFactories.RegisterFactory(MakeShareable(new FEzAbilityTimelineSummoner(InHostingApp, PreviewScene.ToSharedRef())));
+	
 	TabLayout = FTabManager::NewLayout("Standalone_EzAbilityEditor_Layout_v1.0")
 		->AddArea
 		(
@@ -55,9 +59,16 @@ FEzAbilityEditorApplicationMode::FEzAbilityEditorApplicationMode(const TSharedRe
 					(
 						FTabManager::NewStack()
 						->SetSizeCoefficient(0.6f)
-						->SetHideTabWell(false)
+						->SetHideTabWell(true)
 						->AddTab(FEzAbilityViewPortSummoner::EzAbilityEditorViewPortSummonerID, ETabState::OpenedTab)
 					)
+					->Split
+					(
+						FTabManager::NewStack()
+						->SetSizeCoefficient(0.4f)
+						->SetHideTabWell(true)
+						->AddTab(FEzAbilityTimelineSummoner::EzAbilityTimelineSummonerID, ETabState::OpenedTab)
+					)
 				)
 				->Split
 				(

+ 186 - 0
Ability/Plugins/EzAbility/Source/EzAbilityEditor/Private/EzAbilityTimelinePanel.cpp

@@ -0,0 +1,186 @@
+// Copyright (c) Extra Life Studios, LLC. All rights reserved.
+
+#include "EzAbilityTimelinePanel.h"
+
+#include "EdGraph/EdGraph.h"
+#include "Fonts/FontMeasure.h"
+#include "Framework/Application/MenuStack.h"
+#include "Framework/Application/SlateApplication.h"
+#include "Framework/Text/RichTextLayoutMarshaller.h"
+#include "Styling/AppStyle.h"
+#include "Rendering/SlateRenderer.h"
+#include "Widgets/Layout/SBorder.h"
+#include "Widgets/Layout/SBox.h"
+#include "Widgets/Layout/SSpacer.h"
+#include "Widgets/Images/SImage.h"
+#include "Widgets/Input/SButton.h"
+#include "Widgets/Input/SEditableText.h"
+#include "Widgets/Input/SNumericEntryBox.h"
+#include "Widgets/Text/STextBlock.h"
+#include "Widgets/Text/SRichTextBlock.h"
+#include "Widgets/SWindow.h"
+#include "EzAbilityTimelineScrubPanel.h"
+
+#define LOCTEXT_NAMESPACE "AblAbilityEditor"
+
+SEzAbilityTimelinePanel::SEzAbilityTimelinePanel()
+{
+
+}
+
+void SEzAbilityTimelinePanel::Construct(const FArguments& InArgs)
+{
+	ChildSlot
+		[
+			SNew(SBorder)
+				.BorderImage(FCoreStyle::Get().GetBrush("ToolPanel.GroupBorder"))
+				[
+					SNew(SVerticalBox)
+						+ SVerticalBox::Slot()
+						.AutoHeight()
+						.VAlign(VAlign_Top)
+						[
+							SNew(SHorizontalBox)
+								+ SHorizontalBox::Slot()
+								.FillWidth(0.26f)
+								.HAlign(HAlign_Fill)
+								[
+									BuildTimelineControls()
+								]
+								+ SHorizontalBox::Slot()
+								.FillWidth(0.74f)
+								.HAlign(EHorizontalAlignment::HAlign_Fill)
+								[
+									SNew(SEzAbilityTimelineScrubPanel)
+								]
+						]
+				]
+		];
+}
+
+void SEzAbilityTimelinePanel::Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime)
+{
+	SCompoundWidget::Tick(AllottedGeometry, InCurrentTime, InDeltaTime);
+}
+
+TSharedRef<SWidget> SEzAbilityTimelinePanel::BuildTimelineControls()
+{
+	return
+		SNew(SBorder)
+		.BorderImage(FCoreStyle::Get().GetBrush("ToolPanel.GroupBorder"))
+		[
+			SNew(SHorizontalBox)
+				+ SHorizontalBox::Slot()
+				.Padding(1.0f, 2.0f)
+				.HAlign(HAlign_Left)
+				.AutoWidth()
+				[
+					SNew(SButton)
+						.ButtonStyle(FAppStyle::Get(), "NoBorder")
+						.ToolTipText(LOCTEXT("StepBack", "Step Back"))
+						.ContentPadding(2.0f)
+						[
+							SNew(SImage)
+								.Image(FAppStyle::GetBrush("WhiteBrush"))
+						]
+				]
+				+ SHorizontalBox::Slot()
+				.Padding(1.0f, 2.0f)
+				.HAlign(HAlign_Left)
+				.AutoWidth()
+				[
+					SNew(SButton)
+						.ButtonStyle(FAppStyle::Get(), "NoBorder")
+						.ToolTipText(LOCTEXT("Stop", "Stop"))
+						.ContentPadding(2.0f)
+						[
+							SNew(SImage)
+								.Image(FAppStyle::GetBrush("WhiteBrush"))
+						]
+				]
+				+ SHorizontalBox::Slot()
+				.Padding(1.0f, 2.0f)
+				.HAlign(HAlign_Left)
+				.AutoWidth()
+				[
+					SNew(SButton)
+						.ButtonStyle(FAppStyle::Get(), "NoBorder")
+						//.OnClicked(this, &SAblAbilityTimelinePanel::OnPlayOrPause)
+						//.ToolTipText(this, &SAblAbilityTimelinePanel::GetPlayPauseToolTip)
+						.ContentPadding(2.0f)
+						[
+							SNew(SImage)
+								.Image(FAppStyle::GetBrush("WhiteBrush"))
+						]
+				]
+				+ SHorizontalBox::Slot()
+				.Padding(1.0f, 2.0f)
+				.HAlign(HAlign_Left)
+				.AutoWidth()
+				[
+					SNew(SButton)
+						.ButtonStyle(FAppStyle::Get(), "NoBorder")
+						//.OnClicked(this, &SAblAbilityTimelinePanel::OnStepForwards)
+						.ToolTipText(LOCTEXT("StepForward", "Step Forward"))
+						.ContentPadding(2.0f)
+						[
+							SNew(SImage)
+								.Image(FAppStyle::GetBrush("WhiteBrush"))
+						]
+				]
+
+				+ SHorizontalBox::Slot()
+				.HAlign(HAlign_Left)
+				.AutoWidth()
+				[
+					SNew(SSpacer)
+						.Size(FVector2D(16.0f, 1.0f))
+				]
+
+				+ SHorizontalBox::Slot()
+				.HAlign(HAlign_Left)
+				.VAlign(VAlign_Center)
+				.AutoWidth()
+				[
+					SNew(SNumericEntryBox<float>)
+						.Font(FAppStyle::GetFontStyle(TEXT("PropertyWindow.NormalFont")))
+						.AllowSpin(false)
+						//.MinValue(this, &SAblAbilityTimelinePanel::GetTimeMin)
+						//.MaxValue(this, &SAblAbilityTimelinePanel::GetTimeMax)
+						//.Value(this, &SAblAbilityTimelinePanel::GetCurrentTime)
+						//.OnValueCommitted(this, &SAblAbilityTimelinePanel::OnTimeValueCommitted)
+						//.ToolTipText(this, &SAblAbilityTimelinePanel::GetTimeTooltipText)
+						.Label()
+						[
+							SNumericEntryBox<float>::BuildLabel(LOCTEXT("AblTimelineTimeLabel", "Time"), FLinearColor::White, FLinearColor(0.2f, 0.2f, 0.2f))
+						]
+				]
+
+				+ SHorizontalBox::Slot()
+				.HAlign(HAlign_Left)
+				.AutoWidth()
+				[
+					SNew(SSpacer)
+						.Size(FVector2D(16.0f, 1.0f))
+				]
+
+				+ SHorizontalBox::Slot()
+				.HAlign(HAlign_Left)
+				.VAlign(VAlign_Center)
+				.AutoWidth()
+				[
+					SNew(SNumericEntryBox<int>)
+						.Font(FAppStyle::GetFontStyle(TEXT("PropertyWindow.NormalFont")))
+						.AllowSpin(true)
+						//.MinValue(this, &SAblAbilityTimelinePanel::GetFrameMin)
+						//.MaxValue(this, &SAblAbilityTimelinePanel::GetFrameMax)
+						//.Value(this, &SAblAbilityTimelinePanel::GetCurrentFrame)
+						//.OnValueCommitted(this, &SAblAbilityTimelinePanel::OnFrameValueCommitted)
+						//.ToolTipText(this, &SAblAbilityTimelinePanel::GetFramesTooltipText)
+						.Label()
+						[
+							SNumericEntryBox<float>::BuildLabel(LOCTEXT("AblTimelineFrameLabel", "Frame"), FLinearColor::White, FLinearColor(0.2f, 0.2f, 0.2f))
+						]
+				]
+		];
+}

+ 140 - 0
Ability/Plugins/EzAbility/Source/EzAbilityEditor/Private/EzAbilityTimelineScrubPanel.cpp

@@ -0,0 +1,140 @@
+#pragma once
+
+#include "EzAbilityTimelineScrubPanel.h"
+#include "Fonts/FontMeasure.h"
+
+SEzAbilityTimelineScrubPanel::SEzAbilityTimelineScrubPanel()
+{
+
+}
+
+
+void SEzAbilityTimelineScrubPanel::Construct(const FArguments& InArgs)
+{
+	m_Font = FSlateFontInfo(FPaths::EngineContentDir() / TEXT("Slate/Fonts/Roboto-Regular.ttf"), 8);
+	m_Brush = FAppStyle::GetBrush("WhiteBrush");
+}
+
+FVector2D SEzAbilityTimelineScrubPanel::ComputeDesiredSize(float scale) const
+{
+	return FVector2D(100.0f, 40.0f);
+}
+
+int32 SEzAbilityTimelineScrubPanel::OnPaint(const FPaintArgs& Args, const FGeometry& AllottedGeometry, const FSlateRect& MyClippingRect, FSlateWindowElementList& OutDrawElements, int32 LayerId, const FWidgetStyle& InWidgetStyle, bool bParentEnabled) const
+{
+	FVector2D TimeRange(0.0f, 1.0f);
+
+	const TSharedRef< FSlateFontMeasure > FontMeasureService = FSlateApplication::Get().GetRenderer()->GetFontMeasureService();
+
+	const float CurrentPosition = 1;
+	const float AbilityLength = 1;
+	const float TimeRatio = CurrentPosition / AbilityLength;
+
+	FNumberFormattingOptions WholeNumberFmt;
+	WholeNumberFmt.SetMaximumFractionalDigits(0);
+
+	FNumberFormattingOptions FmtOptions;
+	FmtOptions.SetMaximumFractionalDigits(2);
+	FmtOptions.SetMinimumFractionalDigits(1);
+
+	FText MinText = FText::AsNumber(TimeRange.X, &WholeNumberFmt);
+	FText MaxText = FText::AsNumber(TimeRange.Y, &WholeNumberFmt);
+	FVector2D MinSize = FontMeasureService->Measure(MinText, m_Font);
+	FVector2D MaxSize = FontMeasureService->Measure(MaxText, m_Font);
+
+	const FVector2D& WidgetSize = AllottedGeometry.GetLocalSize();
+
+	// Our Padding is how much it takes to safely display our largest string.
+	const float Padding = MaxSize.X * 0.5f + 4.0f;
+	const float ScrollbarWidth = 12.0f;
+	const float VertPadding = 4.0f;
+	FVector2D TextOffset(0.0f, VertPadding);
+
+
+	int32 CurrentLayer = LayerId;
+
+	FSlateDrawElement::MakeBox(OutDrawElements,
+		CurrentLayer++,
+		AllottedGeometry.ToPaintGeometry(),
+		m_Brush);
+
+	FSlateLayoutTransform Transform;
+
+
+	// Right side (Max Time Label)
+	TextOffset.X = WidgetSize.X - MaxSize.X * 0.5f - Padding - ScrollbarWidth;
+
+	Transform = FSlateLayoutTransform(TextOffset);
+
+	FSlateDrawElement::MakeText(OutDrawElements,
+		CurrentLayer++,
+		AllottedGeometry.ToPaintGeometry(Transform),
+		MaxText,
+		m_Font);
+
+	// Lines
+	float MajorLineSize = WidgetSize.Y * 0.45f;
+	float MinorLineSize = WidgetSize.Y * 0.20f;
+
+	TArray<FVector2D> Line; // Start/End points.
+	Line.SetNum(2);
+
+	float MajorFreq = 1;
+	float MinorFreq = 1;
+
+	// Major
+	float StepTime = 0.0f;
+	FText MajorLabel;
+
+	Line[0].Y = WidgetSize.Y - 1.0f - VertPadding; // Bottom, minus a bit of padding.
+	Line[1].Y = WidgetSize.Y - MajorLineSize + VertPadding;
+
+
+	const float WidgetInteriorSize = WidgetSize.X - Padding * 2.0f - ScrollbarWidth; // We have padding on both ends.
+
+	for (; StepTime < TimeRange.Y; StepTime += MajorFreq)
+	{
+		Line[0].X = Padding + WidgetInteriorSize * (StepTime / TimeRange.Y);
+		Line[1].X = Line[0].X;
+
+		FSlateDrawElement::MakeLines(OutDrawElements,
+			CurrentLayer++,
+			AllottedGeometry.ToPaintGeometry(),
+			Line);
+	}
+
+	// Minor
+	for (StepTime = 0.0f; StepTime < TimeRange.Y; StepTime += MinorFreq)
+	{
+		Line[0].X = Padding + WidgetInteriorSize * (StepTime / TimeRange.Y);
+		Line[1].X = Line[0].X;
+
+		FSlateDrawElement::MakeLines(OutDrawElements,
+			CurrentLayer++,
+			AllottedGeometry.ToPaintGeometry(),
+			Line);
+	}
+
+	// Far Right Line
+	Line[0].X = WidgetSize.X - Padding - ScrollbarWidth;
+	Line[1].X = Line[0].X;
+
+	FSlateDrawElement::MakeLines(OutDrawElements,
+		CurrentLayer++,
+		AllottedGeometry.ToPaintGeometry(),
+		Line);
+
+	// Draw our Marker Icon
+	FVector2D MarkerSize(12.0f, 12.0f);
+	FVector2D MarkerOffset;
+
+	// Our Marker track goes up to the line we use to separate the time value from the rest of the widget.
+	MarkerOffset.X = (Padding + WidgetInteriorSize * TimeRatio - MarkerSize.X * 0.5f);
+	MarkerOffset.Y = 4; // Put it under our outline.
+
+	Transform = FSlateLayoutTransform(MarkerOffset);
+
+	FSlateDrawElement::MakeBox(OutDrawElements, CurrentLayer++, AllottedGeometry.ToPaintGeometry(MarkerSize, Transform), FAppStyle::GetBrush("WhiteBrush"));
+
+	return SCompoundWidget::OnPaint(Args, AllottedGeometry, MyClippingRect, OutDrawElements, CurrentLayer, InWidgetStyle, bParentEnabled);
+}

+ 3 - 1
Ability/Plugins/EzAbility/Source/EzAbilityEditor/Private/EzAbilityTimelineSummoner.cpp

@@ -8,6 +8,8 @@
 #include "Styling/CoreStyle.h"
 #include "SAdvancedPreviewDetailsTab.h"
 #include "SEditorViewport.h"
+#include "EzAbilityTimelinePanel.h"
+
 #define LOCTEXT_NAMESPACE "AbilityModes"
 
 /////////////////////////////////////////////////////
@@ -48,7 +50,7 @@ FEzAbilityTimelineSummoner::FEzAbilityTimelineSummoner(TSharedPtr<class FAssetEd
 TSharedRef<SWidget> FEzAbilityTimelineSummoner::CreateTabBody(const FWorkflowTabSpawnInfo& Info) const
 {
 
-	return SNew(SAbilityEditorViewport);
+	return SNew(SEzAbilityTimelinePanel);
 	// 	return SNew(SButton)
 	// 		.VAlign(VAlign_Center)
 	// 		.HAlign(HAlign_Center)

+ 28 - 0
Ability/Plugins/EzAbility/Source/EzAbilityEditor/Public/EzAbilityTimelinePanel.h

@@ -0,0 +1,28 @@
+
+#pragma once
+
+#include "Fonts/SlateFontInfo.h"
+#include "Widgets/Layout/SScrollBox.h"
+#include "Widgets/Text/SRichTextBlock.h"
+#include "Widgets/SCompoundWidget.h"
+
+class UEdGraph;
+
+/* Timeline Panel is a widget that displays all the Tasks in our Ability. When a Task is added or removed, the widget will update itself appropriately. */
+class SEzAbilityTimelinePanel : public SCompoundWidget
+{
+public:
+	SLATE_BEGIN_ARGS(SEzAbilityTimelinePanel)
+		{}
+		//SLATE_ATTRIBUTE(TObjectPtr<UMBRData>, TestMBR)
+	SLATE_END_ARGS()
+
+	SEzAbilityTimelinePanel();
+
+	void Construct(const FArguments& InArgs);
+
+	// Tick Override 
+	virtual void Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) override;
+
+	TSharedRef<SWidget> BuildTimelineControls();
+};

+ 30 - 0
Ability/Plugins/EzAbility/Source/EzAbilityEditor/Public/EzAbilityTimelineScrubPanel.h

@@ -0,0 +1,30 @@
+#pragma once
+
+#include "EzAbilityTimelineScrubPanel.h"
+#include "Fonts/SlateFontInfo.h"
+#include "Widgets/SCompoundWidget.h"
+
+/* The Timeline Scrub Panel displays the time of the Ability from 0.0 to Ability Length with optional tick marks defined by the user. */
+class SEzAbilityTimelineScrubPanel : public SCompoundWidget
+{
+public:	
+SLATE_BEGIN_ARGS(SEzAbilityTimelineScrubPanel)
+{}
+	  //SLATE_ATTRIBUTE(TObjectPtr<UMBRData>, TestMBR)
+	  SLATE_END_ARGS()
+
+	  /** Constructs this widget with InArgs */
+	  void Construct(const FArguments& InArgs);
+
+	SEzAbilityTimelineScrubPanel();
+
+	//void Construct();
+	virtual FVector2D ComputeDesiredSize(float scale) const override;
+	virtual int32 OnPaint(const FPaintArgs& Args, const FGeometry& AllottedGeometry, const FSlateRect& MyClippingRect, FSlateWindowElementList& OutDrawElements, int32 LayerId, const FWidgetStyle& InWidgetStyle, bool bParentEnabled) const override;
+	
+	/* Font information for our widget. */
+	FSlateFontInfo m_Font;
+
+	/* Brush for our widget. */
+	const FSlateBrush* m_Brush;
+};