6298 lines
214 KiB
C++
6298 lines
214 KiB
C++
#if __BANK
|
|
|
|
#include "AnimSceneEditor.h"
|
|
#include <time.h>
|
|
|
|
// Rage headers
|
|
#include "bank/group.h"
|
|
#include "bank/msgbox.h"
|
|
#include "grcore/font.h"
|
|
#include "parser/macros.h"
|
|
|
|
// framework headers
|
|
#include "fwdebug/picker.h"
|
|
#include "debug/GtaPicker.h"
|
|
|
|
// game headers
|
|
#include "animation/AnimScene/AnimScene.h"
|
|
#include "animation/AnimScene/AnimSceneManager.h"
|
|
#include "animation/animscene/entities/AnimSceneEntities.h"
|
|
#include "animation/AnimScene/entities/AnimSceneEntityInitialisers.h"
|
|
#include "animation/AnimScene/events/AnimScenePlayAnimEvent.h"
|
|
#include "animation/AnimScene/events/AnimScenePlayCameraAnimEvent.h"
|
|
#include "animation/AnimScene/events/AnimSceneEventInitialisers.h"
|
|
#include "AnimSceneScrollbar.h"
|
|
#include "animation/debug/AnimDebug.h"
|
|
#include "peds/ped.h"
|
|
#include "scene/physical.h"
|
|
#include "system/controlMgr.h"
|
|
#include "debug/DebugScene.h"
|
|
#include "text/Text.h"
|
|
|
|
ANIM_OPTIMISATIONS()
|
|
|
|
//--------------------------------------------------------------------------------
|
|
// VERSION NUMBER
|
|
//--------------------------------------------------------------------------------
|
|
#define ASE_MAJOR_VERSION (0)
|
|
#define ASE_MINOR_VERSION (2)
|
|
|
|
// Version number text color
|
|
#define ASE_VersionColor (Color32(242, 242, 242, 160))
|
|
#define ASE_VersionShadowColor (Color32(0, 0, 0, 255))
|
|
|
|
// Picker color
|
|
#define ASE_EntityPickerBoundingBoxColor (Color32(255, 0, 0, 255))
|
|
|
|
//Panel Colors
|
|
#define ASE_Panel_BackGroundColor (Color32(0, 0, 0, 128))
|
|
#define ASE_Panel_BackGroundColorDark (Color32(0, 0, 0, 160))
|
|
#define ASE_Panel_OutlineColor (Color32(242, 242, 242, 160))
|
|
#define ASE_Panel_ReadOnlyTextColor (Color32(256, 256, 256, 128))
|
|
|
|
|
|
//Panel Button Color
|
|
#define ASE_Panel_Button_Color (Color32(242, 242, 242, 160))
|
|
#define ASE_Panel_Button_BackGroundColor (Color32(0, 0, 0, 128))
|
|
#define ASE_Panel_Button_HoverBackgroundColor (Color32(20, 20, 20, 160))
|
|
|
|
#define ASE_Panel_Button_HoverColor (Color32(255, 255, 255, 255))
|
|
#define ASE_Panel_Button_ActiveHoverColor (Color32(255, 255, 255, 255))
|
|
|
|
#define ASE_Panel_Button_ActiveColor (Color32(242, 242, 242, 160))
|
|
#define ASE_Panel_Button_ActiveBackgroundColor (Color32(40, 40, 40, 180))
|
|
#define ASE_Panel_Button_ActiveOutlineColor (Color32(256, 0, 0, 160))
|
|
#define ASE_Panel_Button_OutlineColor (Color32(256, 0, 0, 160))
|
|
|
|
//Text Colours
|
|
#define ASE_Editor_DefaultTextColor (Color32(242, 242, 242, 160))
|
|
#define ASE_Editor_DefaultTextOutlineColor (Color32(200, 200, 200, 128))
|
|
#define ASE_Editor_DefaultTextBackgroundColor (Color32(0, 0, 0, 128))
|
|
#define ASE_Editor_HoveredTextColor (Color32(242, 242, 242, 160))
|
|
#define ASE_Editor_WarningTextColor (Color32(255, 204, 0, 160))
|
|
|
|
#define ASE_Editor_SelectedTextColor (Color32(242, 242, 242, 160))
|
|
#define ASE_Editor_SelectedTextOutlineColor (Color32(256, 0, 0, 100))
|
|
#define ASE_Editor_FocusTextOutlineColor (Color32(256, 0, 0, 200))
|
|
#define ASE_Editor_SelectedTextBackgroundColor (Color32(0, 0, 0, 160))
|
|
#define ASE_Editor_SelectedHoveredTextColor (Color32(255, 255, 255, 160))
|
|
|
|
#define ASE_Editor_DisabledTextColor (Color32(160, 160, 160, 90))
|
|
#define ASE_Editor_DisabledOutlineColor (Color32(160, 160, 160, 90))
|
|
#define ASE_Editor_DisabledBackgroundColor (Color32(0, 0, 0, 90))
|
|
|
|
//Event Colors
|
|
#define ASE_Panel_EventColor (Color32(0, 0, 0, 128))
|
|
|
|
#define ASE_Panel_EventBakerlooBrownColor (Color32(179, 99, 5, 255))
|
|
#define ASE_Panel_EventCentraRedColor (Color32(227, 32, 23, 255))
|
|
#define ASE_Panel_EventCircleYellowColor (Color32(255, 211, 0, 255))
|
|
#define ASE_Panel_EventDistrictGreen (Color32(0, 120, 42, 255))
|
|
#define ASE_Panel_EventHCPinkColor (Color32(243, 169, 187, 255))
|
|
#define ASE_Panel_EventJubileeGreyColor (Color32(160, 165, 169, 255))
|
|
#define ASE_Panel_EventMetropolitanPurpleColor (Color32(155, 0, 86, 255))
|
|
#define ASE_Panel_EventNorthernBlackColor (Color32(0, 0, 0, 255))
|
|
#define ASE_Panel_EventPiccadilyBlueColor (Color32(0, 54, 136, 255))
|
|
#define ASE_Panel_EventVictoriaBlueColor (Color32(0, 152, 212, 255))
|
|
#define ASE_Panel_EventWCGreenColor (Color32(149, 205, 186, 255))
|
|
#define ASE_Panel_EventDLRBluekColor (Color32(0, 164, 167, 255))
|
|
#define ASE_Panel_EventOGOrangeColor (Color32(238, 124, 14, 255))
|
|
#define ASE_Panel_EventTLGreenColor (Color32(132, 184, 23, 255))
|
|
|
|
#define ASE_Panel_EventMarkerColor (Color32(255, 255, 255, 128))
|
|
#define ASE_Panel_EventOutlineColor (Color32(255, 255, 255, 128))
|
|
#define ASE_Panel_EventBackgroundColor (Color32(200, 200, 255, 128))
|
|
|
|
#define ASE_Panel_SelectedEventColor (Color32(0, 0, 0, 192))
|
|
#define ASE_Panel_SelectedEventMarkerColor (Color32(256, 0, 0, 192))
|
|
#define ASE_Panel_SelectedEventOutlineColor (Color32(256, 0, 0, 192))
|
|
#define ASE_Panel_SelectedEventDraggingColor (Color32(180, 75, 256, 255))
|
|
|
|
#define ASE_Panel_EventPreloadlineColor (Color32(0, 0, 0, 160))
|
|
#define ASE_Panel_EventCurrentTimeLineColor (Color32(180, 180, 180, 255))
|
|
|
|
// Timeline Colors
|
|
#define ASE_Timeline_Marker1FrameColor (Color32(64, 64, 64, 160))
|
|
#define ASE_Timeline_Marker5FrameColor (Color32(96, 96, 96, 160))
|
|
#define ASE_Timeline_Marker30FrameColor (Color32(128, 128, 128, 160))
|
|
|
|
float CAnimSceneEditor::EventLayer::ms_layerHeight = 15.0f;
|
|
bool CAnimSceneEditor::m_editorSettingUseSmoothFont = false;
|
|
bool CAnimSceneEditor::m_editorSettingLoopPlayback = false;
|
|
bool CAnimSceneEditor::m_editorSettingHoldAtLastFrame = true;
|
|
bool CAnimSceneEditor::m_editorSettingHideEvents = false;
|
|
float CAnimSceneEditor::ms_editorSettingBackgroundAlpha = 0.5f;
|
|
bool CAnimSceneEditor::ms_editorSettingUseEventColourForMarker = true;
|
|
|
|
//TUNE_FLOAT(ms_layerHeight, 30.0f, 0.0f, 100.0f, 1.0f)
|
|
//TUNE_FLOAT(ButtonWidth, 50.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
//--------------------------------------------------------------------------------
|
|
// TEXT RENDERING
|
|
//--------------------------------------------------------------------------------
|
|
|
|
// NOTE: This is pretty hard-coded at the moment due to Scaleform font details.
|
|
// The Scaleform font's already have some padding, so we have to counter-act that to give us the precise text positioning and sizing we desire.
|
|
// The Scaleform font rendering is also based on normalised screen space, where as Anim Scene Editor layout code uses pixels, so we have to convert accordingly.
|
|
|
|
// NOTE: Any hard-coded values below were calculated when the scale was 1.0, and hence scaled accordingly.
|
|
|
|
// Overall scale. This defines the overall scaling of the font, and these values are based on the debug information bar at the bottom of the screen. See bar.cpp
|
|
const float fTextOverallScaleX = 0.1f;
|
|
const float fTextOverallScaleY = 0.3f;
|
|
|
|
const float fTextOverallSizeScale = 0.9f;
|
|
|
|
// Calculate the final scaling
|
|
const float fFinalTextScaleX = fTextOverallScaleX * fTextOverallSizeScale;
|
|
const float fFinalTextScaleY = fTextOverallScaleY * fTextOverallSizeScale;
|
|
|
|
// Scaleform has some built in padding. Remember this as an offset for when we come to render the actual text.
|
|
// This padding value is based on the space above and below the CAPITAL letters.
|
|
const float fScaleformTextFixedVerticalOffset = 2.0f;
|
|
const float fScaleformTextVerticalPaddingTop = fScaleformTextFixedVerticalOffset + (11.0f * fTextOverallScaleY);
|
|
const float fScaleformTextVerticalPaddingBottom = 13.0f * fTextOverallScaleY;
|
|
|
|
// Text Helper functions
|
|
float GetTextWidth(const char* pText)
|
|
{
|
|
Assert(pText);
|
|
|
|
if (CAnimSceneEditor::GetUseSmoothFont())
|
|
{
|
|
CTextLayout textLayout;
|
|
textLayout.SetScale(Vector2(fFinalTextScaleX, fFinalTextScaleY));
|
|
|
|
// Get width and scale back to pixels
|
|
return textLayout.GetStringWidthOnScreen(pText, true) * (float)GRCDEVICE.GetWidth();
|
|
}
|
|
else
|
|
{
|
|
return (float)grcFont::GetCurrent().GetStringWidth(pText, (int)strlen(pText));
|
|
}
|
|
}
|
|
|
|
float GetTextHeight()
|
|
{
|
|
if (CAnimSceneEditor::GetUseSmoothFont())
|
|
{
|
|
CTextLayout textLayout;
|
|
textLayout.SetScale(Vector2(fFinalTextScaleX, fFinalTextScaleY));
|
|
|
|
return textLayout.GetCharacterHeight() * (float)GRCDEVICE.GetHeight();
|
|
}
|
|
else
|
|
{
|
|
return (float)grcFont::GetCurrent().GetHeight();
|
|
}
|
|
}
|
|
|
|
void RenderText(const char* pText, float posX, float posY, const Color32& textColour)
|
|
{
|
|
Assert(pText);
|
|
|
|
grcLighting(false);
|
|
|
|
if (CAnimSceneEditor::GetUseSmoothFont())
|
|
{
|
|
CTextLayout textLayout;
|
|
textLayout.SetColor(textColour);
|
|
textLayout.SetScale(Vector2(fFinalTextScaleX, fFinalTextScaleY));
|
|
textLayout.SetWrap(Vector2(0.f,2.f));//don't wrap (only do so far past the right hand side of the screen)
|
|
// TODO - get proper screen dimensions
|
|
textLayout.Render(Vector2(posX * (1.0f / (float)GRCDEVICE.GetWidth()), (posY - fScaleformTextVerticalPaddingTop) * (1.0f / (float)GRCDEVICE.GetHeight())), pText);
|
|
CText::Flush();
|
|
}
|
|
else
|
|
{
|
|
grcColor(textColour);
|
|
grcDraw2dText(posX, posY, pText);
|
|
}
|
|
}
|
|
|
|
void RenderTextWithBackground(const char* pText, float posX, float posY, const Color32& textColour, const Color32& backgroundColour, float fBackGroundPadding = 0.0f, bool renderOutline = false, const Color32& outlineColour = ASE_Editor_DefaultTextOutlineColor)
|
|
{
|
|
Assert(pText);
|
|
|
|
grcLighting(false);
|
|
|
|
const float fFontHeight = GetTextHeight();
|
|
const float fTextWidth = GetTextWidth(pText);
|
|
|
|
// Render background
|
|
if (fBackGroundPadding >= 0.0f)
|
|
{
|
|
grcColor(backgroundColour);
|
|
grcBegin(drawTriStrip, 4);
|
|
grcVertex2f(posX - fBackGroundPadding, posY - fBackGroundPadding);
|
|
grcVertex2f(posX + fBackGroundPadding + fTextWidth, posY - fBackGroundPadding);
|
|
grcVertex2f(posX - fBackGroundPadding, posY + fBackGroundPadding + fFontHeight - (CAnimSceneEditor::GetUseSmoothFont() ? fScaleformTextVerticalPaddingBottom : 0.0f));
|
|
grcVertex2f(posX + fBackGroundPadding + fTextWidth, posY + fBackGroundPadding + fFontHeight - (CAnimSceneEditor::GetUseSmoothFont() ? fScaleformTextVerticalPaddingBottom : 0.0f));
|
|
grcEnd();
|
|
|
|
if(renderOutline)
|
|
{
|
|
grcColor(outlineColour);
|
|
grcBegin(drawLineStrip, 5);
|
|
grcVertex2f(posX - fBackGroundPadding, posY - fBackGroundPadding);
|
|
grcVertex2f(posX + fBackGroundPadding + fTextWidth, posY - fBackGroundPadding);
|
|
grcVertex2f(posX + fBackGroundPadding + fTextWidth, posY + fBackGroundPadding + fFontHeight - (CAnimSceneEditor::GetUseSmoothFont() ? fScaleformTextVerticalPaddingBottom : 0.0f));
|
|
grcVertex2f(posX - fBackGroundPadding, posY + fBackGroundPadding + fFontHeight - (CAnimSceneEditor::GetUseSmoothFont() ? fScaleformTextVerticalPaddingBottom : 0.0f));
|
|
grcVertex2f(posX - fBackGroundPadding, posY - fBackGroundPadding);
|
|
grcEnd();
|
|
}
|
|
}
|
|
|
|
if (CAnimSceneEditor::GetUseSmoothFont())
|
|
{
|
|
CTextLayout textLayout;
|
|
textLayout.SetColor(textColour);
|
|
textLayout.SetScale(Vector2(fFinalTextScaleX, fFinalTextScaleY));
|
|
textLayout.SetWrap(Vector2(0.f,2.f));//don't wrap (only do so far past the right hand side of the screen)
|
|
// TODO - get proper screen dimensions
|
|
textLayout.Render(Vector2(posX * (1.0f / (float)GRCDEVICE.GetWidth()), (posY - fScaleformTextVerticalPaddingTop) * (1.0f / (float)GRCDEVICE.GetHeight())), pText);
|
|
CText::Flush();
|
|
}
|
|
else
|
|
{
|
|
grcColor(textColour);
|
|
grcDraw2dText(posX, posY, pText);
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// CScreenExtents
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
void CScreenExtents::DrawBorder(Color32 color)
|
|
{
|
|
grcColor(color);
|
|
grcBegin(drawLineStrip, 5);
|
|
grcVertex2f(m_min.x, m_min.y);
|
|
grcVertex2f(m_min.x, m_max.y);
|
|
grcVertex2f(m_max.x, m_max.y);
|
|
grcVertex2f(m_max.x, m_min.y);
|
|
grcVertex2f(m_min.x, m_min.y);
|
|
grcEnd();
|
|
}
|
|
|
|
//--------------------------------------------------------------------------------
|
|
// CSceneInformationDisplay
|
|
//--------------------------------------------------------------------------------
|
|
|
|
CSceneInformationDisplay::CSceneInformationDisplay()
|
|
{
|
|
|
|
}
|
|
|
|
CSceneInformationDisplay::CSceneInformationDisplay(const CScreenExtents& screenExtents)
|
|
{
|
|
m_screenExtents = screenExtents;
|
|
}
|
|
|
|
CSceneInformationDisplay::~CSceneInformationDisplay()
|
|
{
|
|
|
|
}
|
|
|
|
// PURPOSE: Set the screen extents of the display
|
|
void CSceneInformationDisplay::SetScreenExtents(const CScreenExtents& screenExtents)
|
|
{
|
|
m_screenExtents = screenExtents;
|
|
}
|
|
|
|
// PURPOSE: Call once per frame to update the display
|
|
void CSceneInformationDisplay::Process(float fCurrentTime, float fTotalSceneTime)
|
|
{
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render - background and outline
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
// Render dark background
|
|
grcColor(GetColor(kDisplayBackgroundColor));
|
|
grcBegin(drawTriStrip, 4);
|
|
{
|
|
grcVertex2f(m_screenExtents.GetMinX(), m_screenExtents.GetMinY());
|
|
grcVertex2f(m_screenExtents.GetMaxX(), m_screenExtents.GetMinY());
|
|
grcVertex2f(m_screenExtents.GetMinX(), m_screenExtents.GetMaxY());
|
|
grcVertex2f(m_screenExtents.GetMaxX(), m_screenExtents.GetMaxY());
|
|
}
|
|
grcEnd();
|
|
|
|
// Render display white outline
|
|
grcColor(GetColor(kDisplayOutlineColor));
|
|
grcBegin(drawLineStrip, 5);
|
|
{
|
|
grcVertex2f(m_screenExtents.GetMinX(), m_screenExtents.GetMinY());
|
|
grcVertex2f(m_screenExtents.GetMaxX(), m_screenExtents.GetMinY());
|
|
grcVertex2f(m_screenExtents.GetMaxX(), m_screenExtents.GetMaxY());
|
|
grcVertex2f(m_screenExtents.GetMinX(), m_screenExtents.GetMaxY());
|
|
grcVertex2f(m_screenExtents.GetMinX(), m_screenExtents.GetMinY());
|
|
}
|
|
grcEnd();
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render - Information
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
const float fSidePadding = 3.0f;
|
|
const float fTopLineY = m_screenExtents.GetMinY() + fSidePadding;
|
|
const float fBottomLineY = fTopLineY + (((m_screenExtents.GetMaxY() - m_screenExtents.GetMinY()) - (fSidePadding * 2.0f)) * 0.5f);
|
|
|
|
atVarString currentTimeStr("%.2f", fCurrentTime);
|
|
atVarString totalTimeStr("/ %.2f", fTotalSceneTime);
|
|
|
|
atVarString currentFrameStr("%d", (int)(fCurrentTime * 30.0f));
|
|
atVarString totalFrameStr("/ %d", (int)(fTotalSceneTime * 30.0f));
|
|
|
|
float fTotalTimeWidth = GetTextWidth(totalTimeStr.c_str());
|
|
float fTotalFrameWidth = GetTextWidth(totalFrameStr.c_str());
|
|
|
|
float fTotalsX = m_screenExtents.GetMaxX() - fSidePadding - (fTotalTimeWidth > fTotalFrameWidth ? fTotalTimeWidth : fTotalFrameWidth);
|
|
|
|
atString frameLabel("FRAME: ");
|
|
atString timeLabel("TIME: ");
|
|
|
|
float fCurrentsX = m_screenExtents.GetMinX() + GetTextWidth(frameLabel.c_str()) + fSidePadding;
|
|
|
|
// Key
|
|
RenderText(frameLabel.c_str(), m_screenExtents.GetMinX() + fSidePadding, fTopLineY, m_textColour);
|
|
RenderText(timeLabel.c_str(), m_screenExtents.GetMinX() + fSidePadding, fBottomLineY, m_textColour);
|
|
|
|
// Totals
|
|
RenderText(totalFrameStr.c_str(), fTotalsX, fTopLineY, m_textColour);
|
|
RenderText(totalTimeStr.c_str(), fTotalsX, fBottomLineY, m_textColour);
|
|
|
|
// Current Times
|
|
RenderText(currentFrameStr.c_str(), fCurrentsX, fTopLineY, m_textColour);
|
|
RenderText(currentTimeStr.c_str(), fCurrentsX, fBottomLineY, m_textColour);
|
|
}
|
|
|
|
Color32 CSceneInformationDisplay::GetColor(eColorType type)
|
|
{
|
|
switch (type)
|
|
{
|
|
case CSceneInformationDisplay::kDisplayOutlineColor:
|
|
return Color32(200, 200, 200, 128);
|
|
case CSceneInformationDisplay::kDisplayBackgroundColor:
|
|
return Color32(0, 0, 0, 128);
|
|
|
|
default:
|
|
return Color32(0,0,0,0);
|
|
}
|
|
}
|
|
|
|
//--------------------------------------------------------------------------------
|
|
// COnScreenTimeline
|
|
//--------------------------------------------------------------------------------
|
|
|
|
CAuthoringHelperDisplay::CAuthoringHelperDisplay()
|
|
{
|
|
Init();
|
|
}
|
|
|
|
CAuthoringHelperDisplay::~CAuthoringHelperDisplay()
|
|
{
|
|
|
|
}
|
|
|
|
void CAuthoringHelperDisplay::Process()
|
|
{
|
|
Vector3 points[4];
|
|
points[0].Set(m_screenExtents.GetMinX(), m_screenExtents.GetMinY(), 0.0f);
|
|
points[1].Set(m_screenExtents.GetMinX(), m_screenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(m_screenExtents.GetMaxX(), m_screenExtents.GetMaxY(), 0.0f);
|
|
points[3].Set(m_screenExtents.GetMaxX(), m_screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(points, 4, NULL, true, GetColor(kVideoControlPanelBackgroundColor) );
|
|
|
|
Vector3 borderPoints[4];
|
|
borderPoints[0].Set(m_screenExtents.GetMinX(), m_screenExtents.GetMinY(), 0.0f);
|
|
borderPoints[1].Set(m_screenExtents.GetMinX(), m_screenExtents.GetMaxY(), 0.0f);
|
|
borderPoints[2].Set(m_screenExtents.GetMaxX(), m_screenExtents.GetMaxY(), 0.0f);
|
|
borderPoints[3].Set(m_screenExtents.GetMaxX(), m_screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(borderPoints, 4, NULL, false, GetColor(kVideoControlPanelOutlineColor) );
|
|
|
|
|
|
for(int i =0; i < kMaxNumButtons; i++)
|
|
{
|
|
m_buttons[i].Update();
|
|
m_buttons[i].Draw();
|
|
}
|
|
}
|
|
|
|
void CAuthoringHelperDisplay::SetScreenExtents(const CScreenExtents& screenExtents)
|
|
{
|
|
TUNE_FLOAT(ButtonWidth, 50.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
m_screenExtents = screenExtents;
|
|
|
|
for(int i=0; i < kMaxNumButtons; i ++)
|
|
{
|
|
float minX = m_screenExtents.GetMinX() + (ButtonWidth * i);
|
|
float maxX = m_screenExtents.GetMinX() + (ButtonWidth * i) + ButtonWidth;
|
|
m_buttons[i].SetScreenExtents(CScreenExtents(minX, m_screenExtents.GetMinY(), maxX, m_screenExtents.GetMaxY()));
|
|
}
|
|
}
|
|
|
|
void CAuthoringHelperDisplay::SetColor(u32 colorType, Color32 color)
|
|
{
|
|
if(colorType < kMaxNumColors)
|
|
{
|
|
m_colors[colorType] = color;
|
|
}
|
|
}
|
|
|
|
COnScreenButton* CAuthoringHelperDisplay::GetButton(const u32& button)
|
|
{
|
|
if(button < kMaxNumButtons)
|
|
{
|
|
return &m_buttons[button];
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
Color32 CAuthoringHelperDisplay::GetColor(eColorType type)
|
|
{
|
|
if(type < kMaxNumColors)
|
|
{
|
|
return m_colors[type];
|
|
}
|
|
|
|
return Color32(0,0,0,0);
|
|
}
|
|
|
|
bool CAuthoringHelperDisplay::DrawButtonBackground(const CScreenExtents& screenExtents, const u32& button)
|
|
{
|
|
if(m_buttons[button].WasPressed())
|
|
{
|
|
Vector3 points[4];
|
|
points[0].Set(screenExtents.GetMinX(), screenExtents.GetMinY(), 0.0f);
|
|
points[1].Set(screenExtents.GetMinX(), screenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(screenExtents.GetMaxX(), screenExtents.GetMaxY(), 0.0f);
|
|
points[3].Set(screenExtents.GetMaxX(), screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(points, 4, NULL, false, GetColor(kVideoControlActiveButtonBackgroundColor) );
|
|
}
|
|
|
|
if(m_buttons[button].IsActive() || m_buttons[button].IsHeld())
|
|
{
|
|
Vector3 bgpoints[4];
|
|
bgpoints[0].Set(screenExtents.GetMinX(), screenExtents.GetMinY(), 0.0f);
|
|
bgpoints[1].Set(screenExtents.GetMinX(), screenExtents.GetMaxY(), 0.0f);
|
|
bgpoints[2].Set(screenExtents.GetMaxX(), screenExtents.GetMaxY(), 0.0f);
|
|
bgpoints[3].Set(screenExtents.GetMaxX(), screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(bgpoints, 4, NULL, true, GetColor(kVideoControlActiveButtonBackgroundColor) );
|
|
|
|
Vector3 outlinePoints[4];
|
|
outlinePoints[0].Set(screenExtents.GetMinX(), screenExtents.GetMinY(), 0.0f);
|
|
outlinePoints[1].Set(screenExtents.GetMinX(), screenExtents.GetMaxY(), 0.0f);
|
|
outlinePoints[2].Set(screenExtents.GetMaxX(), screenExtents.GetMaxY(), 0.0f);
|
|
outlinePoints[3].Set(screenExtents.GetMaxX(), screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(outlinePoints, 4, NULL, false, GetColor(kVideoControlPanelActiveButtonOutlineColor) );
|
|
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
void CAuthoringHelperDisplay::Init()
|
|
{
|
|
for(int i=0; i < kMaxNumColors; i ++)
|
|
{
|
|
switch (i)
|
|
{
|
|
case CAuthoringHelperDisplay::kVideoControlPanelBackgroundColor:
|
|
m_colors[i] = Color32(0, 0, 0, 128);
|
|
case CAuthoringHelperDisplay::kVideoControlButtonColor:
|
|
m_colors[i] = Color32(96, 96, 96, 128);
|
|
case CAuthoringHelperDisplay::kVideoControlHoverButtonColor:
|
|
m_colors[i] = Color32(128, 128, 128, 128);
|
|
case CAuthoringHelperDisplay::kVideoControlActiveButtonColor:
|
|
m_colors[i] = Color32(160, 160, 160, 128);
|
|
case CAuthoringHelperDisplay::kVideoControlActiveButtonHighLigtColor:
|
|
m_colors[i] = Color32(192, 192, 192, 128);
|
|
case CAuthoringHelperDisplay::kVideoControlActiveButtonBackgroundColor:
|
|
m_colors[i] = Color32(0, 0, 0, 160);
|
|
case CAuthoringHelperDisplay::kVideoControlPanelOutlineColor:
|
|
m_colors[i] = Color32(128, 128, 128, 128);
|
|
}
|
|
|
|
}
|
|
|
|
for(int i=0; i < kMaxNumButtons; i ++)
|
|
{
|
|
switch (i)
|
|
{
|
|
case kTransGbl:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &CAuthoringHelperDisplay::DrawTransGbl)));
|
|
}
|
|
break;
|
|
|
|
case kTransLcl:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &CAuthoringHelperDisplay::DrawTransLcl)));
|
|
}
|
|
break;
|
|
|
|
case kRotLcl:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &CAuthoringHelperDisplay::DrawRotLcl)));
|
|
}
|
|
break;
|
|
|
|
case kRotGbl:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &CAuthoringHelperDisplay::DrawRotGbl)));
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
void CAuthoringHelperDisplay::DrawTransGbl(const CScreenExtents& screenExtents)
|
|
{
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
float borderOffset = 2.0f;
|
|
|
|
TUNE_FLOAT(Texty, 0.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
float Height = GetTextHeight();
|
|
float yOffset = (Canvas.GetHeight() - Height) / 2.0f;
|
|
|
|
if(DrawButtonBackground(Canvas, kTransGbl))
|
|
{
|
|
// Do not render the label if it's off the end of the timeline
|
|
Color32 textCol = m_buttons[kTransGbl].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor);
|
|
RenderText("T:Gbl", Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + yOffset, textCol);
|
|
}
|
|
else
|
|
{
|
|
Color32 textCol = m_buttons[kTransGbl].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor);
|
|
RenderText("T:Gbl", Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + yOffset, textCol);
|
|
}
|
|
}
|
|
|
|
void CAuthoringHelperDisplay::DrawTransLcl(const CScreenExtents& screenExtents)
|
|
{
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
float borderOffset = 2.0f;
|
|
|
|
float Height = GetTextHeight();
|
|
float yOffset = (Canvas.GetHeight() - Height) / 2.0f;
|
|
|
|
if(DrawButtonBackground(Canvas, kTransLcl))
|
|
{
|
|
// Do not render the label if it's off the end of the timeline
|
|
Color32 textCol = m_buttons[kTransLcl].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor);
|
|
RenderText("T:Lcl", Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + yOffset, textCol);
|
|
}
|
|
else
|
|
{
|
|
Color32 textCol = m_buttons[kTransLcl].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor);
|
|
RenderText("T:Lcl", Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + yOffset, textCol);
|
|
}
|
|
}
|
|
|
|
void CAuthoringHelperDisplay::DrawRotLcl(const CScreenExtents& screenExtents)
|
|
{
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
float borderOffset = 2.0f;
|
|
|
|
TUNE_FLOAT(Texty, 0.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
float Height = GetTextHeight();
|
|
float yOffset = (Canvas.GetHeight() - Height) / 2.0f;
|
|
|
|
if(DrawButtonBackground(Canvas, kRotLcl))
|
|
{
|
|
// Do not render the label if it's off the end of the timeline
|
|
Color32 textCol = m_buttons[kRotLcl].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor);
|
|
RenderText("R:Lcl", Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + yOffset, textCol);
|
|
}
|
|
else
|
|
{
|
|
Color32 textCol = m_buttons[kRotLcl].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor);
|
|
RenderText("R:Lcl", Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + yOffset, textCol);
|
|
}
|
|
}
|
|
|
|
void CAuthoringHelperDisplay::DrawRotGbl(const CScreenExtents& screenExtents)
|
|
{
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
float borderOffset = 2.0f;
|
|
|
|
float Height = GetTextHeight();
|
|
float yOffset = (Canvas.GetHeight() - Height) / 2.0f;
|
|
|
|
TUNE_FLOAT(Texty, 0.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
if(DrawButtonBackground(Canvas, kRotGbl))
|
|
{
|
|
// Do not render the label if it's off the end of the timeline
|
|
Color32 textCol = m_buttons[kRotGbl].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor);
|
|
RenderText("R:Gbl", Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + yOffset, textCol);
|
|
}
|
|
else
|
|
{
|
|
Color32 textCol = m_buttons[kRotGbl].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor);
|
|
RenderText("R:Gbl", Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + yOffset, textCol);
|
|
}
|
|
}
|
|
|
|
|
|
void CAuthoringHelperDisplay::SetCanvasSize(CScreenExtents& screenExtents)
|
|
{
|
|
TUNE_FLOAT(CanvasOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
screenExtents.Set(screenExtents.GetMinX() + CanvasOffset, screenExtents.GetMinY() + CanvasOffset, screenExtents.GetMaxX() - CanvasOffset, screenExtents.GetMaxY() - CanvasOffset);
|
|
}
|
|
|
|
|
|
|
|
COnScreenButton::COnScreenButton()
|
|
:m_drawButtonCB(NULL)
|
|
,m_buttonCB(NULL)
|
|
,m_isActive(false)
|
|
,m_isHeld(false)
|
|
,m_isFocus(false)
|
|
,m_wasPressed(false)
|
|
{
|
|
|
|
}
|
|
|
|
COnScreenButton::COnScreenButton(const CScreenExtents& screenExtents)
|
|
:m_drawButtonCB(NULL)
|
|
,m_buttonCB(NULL)
|
|
,m_isActive(false)
|
|
,m_isHeld(false)
|
|
,m_isFocus(false)
|
|
,m_wasPressed(false)
|
|
{
|
|
m_screenExtents = screenExtents;
|
|
}
|
|
|
|
void COnScreenButton::Draw()
|
|
{
|
|
if (m_drawButtonCB)
|
|
{
|
|
m_drawButtonCB(m_screenExtents);
|
|
}
|
|
}
|
|
|
|
|
|
bool COnScreenButton::IsHoveringOver()
|
|
{
|
|
float mouseX = static_cast<float>(ioMouse::GetX());
|
|
float mouseY = static_cast<float>(ioMouse::GetY());
|
|
|
|
bool hoveringOver = (mouseX>m_screenExtents.GetMinX() && (mouseX<m_screenExtents.GetMaxX()))
|
|
&& (mouseY>m_screenExtents.GetMinY() && mouseY<m_screenExtents.GetMaxY());
|
|
|
|
return hoveringOver;
|
|
|
|
}
|
|
|
|
void COnScreenButton::Update()
|
|
{
|
|
bool leftMouseClicked = ioMouse::GetPressedButtons() & ioMouse::MOUSE_LEFT;
|
|
bool leftMouseHeld = ioMouse::GetButtons() & ioMouse::MOUSE_LEFT;
|
|
bool leftMouseReleased = ioMouse::GetReleasedButtons() & ioMouse::MOUSE_LEFT;
|
|
m_isHeld = false;
|
|
|
|
//hovering over the button
|
|
if(IsHoveringOver())
|
|
{
|
|
//if clicked set to focus
|
|
if(leftMouseClicked && !m_isFocus)
|
|
{
|
|
m_isFocus = true;
|
|
}
|
|
|
|
//if the focus button and hovering change active state
|
|
if(m_isFocus && leftMouseReleased)
|
|
{
|
|
m_isActive = !m_isActive;
|
|
|
|
if(m_isActive)
|
|
{
|
|
m_isActive = m_buttonCB(kButtonPressed);
|
|
}
|
|
else
|
|
{
|
|
m_isActive = m_buttonCB(kButtonReleased);
|
|
}
|
|
m_wasPressed = true;
|
|
|
|
m_isFocus = m_isActive;
|
|
}
|
|
}
|
|
|
|
|
|
if(m_isFocus && (leftMouseClicked || leftMouseHeld))
|
|
{
|
|
m_isHeld = true;
|
|
}
|
|
|
|
|
|
if(m_buttonCB && m_isActive)
|
|
{
|
|
m_isActive = m_buttonCB(kButtonHeld);
|
|
|
|
if(!m_isActive)
|
|
{
|
|
m_isFocus = false;
|
|
m_wasPressed = false;
|
|
}
|
|
}
|
|
|
|
if(!IsHoveringOver())
|
|
{
|
|
if(leftMouseClicked || leftMouseReleased)
|
|
{
|
|
if(!m_isActive)
|
|
{
|
|
m_wasPressed = false;
|
|
m_isFocus = false;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
COnScreenVideoControl::COnScreenVideoControl()
|
|
:m_renderSolid(true)
|
|
{
|
|
Init();
|
|
}
|
|
|
|
COnScreenVideoControl::~COnScreenVideoControl()
|
|
{
|
|
|
|
}
|
|
|
|
void COnScreenVideoControl::SetScreenExtents(const CScreenExtents& screenExtents)
|
|
{
|
|
TUNE_FLOAT(ButtonWidth, 20.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
m_screenExtents = screenExtents;
|
|
|
|
for(int i=0; i < kMaxNumButtons; i ++)
|
|
{
|
|
float minX = m_screenExtents.GetMinX() + (ButtonWidth * i);
|
|
float maxX = m_screenExtents.GetMinX() + (ButtonWidth * i) + ButtonWidth;
|
|
m_buttons[i].SetScreenExtents(CScreenExtents(minX, m_screenExtents.GetMinY(), maxX, m_screenExtents.GetMaxY()));
|
|
}
|
|
}
|
|
|
|
void COnScreenVideoControl::SetColor(u32 colorType, Color32 color)
|
|
{
|
|
if(colorType < kMaxNumColors)
|
|
{
|
|
m_colors[colorType] = color;
|
|
}
|
|
}
|
|
|
|
void COnScreenVideoControl::Init()
|
|
{
|
|
//for(int i=0; i < kMaxNumColors; i ++)
|
|
//{
|
|
// switch (i)
|
|
// {
|
|
// case COnScreenVideoControl::kVideoControlSelectedButtonOutline:
|
|
// m_colors[i] = Color32(256, 0, 0, 160);
|
|
// case COnScreenVideoControl::kVideoControlBackgroundColor:
|
|
// m_colors[i] = Color32(0, 0, 0, 128);
|
|
// case COnScreenVideoControl::kVideoControlButtonColor:
|
|
// m_colors[i] = Color32(96, 96, 96, 128);
|
|
// case COnScreenVideoControl::kVideoControlHoverButtonColor:
|
|
// m_colors[i] = Color32(128, 128, 128, 128);
|
|
// case COnScreenVideoControl::kVideoControlActiveButtonColor:
|
|
// m_colors[i] = Color32(160, 160, 160, 128);
|
|
// case COnScreenVideoControl::kVideoControlActiveButtonHighLigtColor:
|
|
// m_colors[i] = Color32(192, 192, 192, 128);
|
|
// case COnScreenVideoControl::kVideoControlActiveButtonBackgroundColor:
|
|
// m_colors[i] = Color32(0, 0, 0, 160);
|
|
// case COnScreenVideoControl::kVideoControlDisplayOutlineColor:
|
|
// m_colors[i] = Color32(128, 128, 128, 128);
|
|
// case COnScreenVideoControl::kVideoControlPanelActiveButtonOutlineColor:
|
|
// m_colors[i] = Color32(0, 0, 0, 160);
|
|
// case COnScreenVideoControl::kVideoControlPanelButtonOutlineColor:
|
|
// m_colors[i] = Color32(0, 0, 0, 160);
|
|
// }
|
|
//}
|
|
|
|
for(int i=0; i < kMaxNumButtons; i ++)
|
|
{
|
|
switch (i)
|
|
{
|
|
case kPlayForwards:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &COnScreenVideoControl::DrawPlayForwardsButton)));
|
|
}
|
|
break;
|
|
|
|
case kStop:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &COnScreenVideoControl::DrawStopButton)));
|
|
}
|
|
break;
|
|
|
|
case kPlayBackwards:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &COnScreenVideoControl::DrawPlayBackwardsButton)));
|
|
}
|
|
break;
|
|
|
|
case kStepBackwards:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &COnScreenVideoControl::DrawStepBackwardsButton)));
|
|
}
|
|
break;
|
|
|
|
case kStepForwards:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &COnScreenVideoControl::DrawStepForwardsButton)));
|
|
}
|
|
break;
|
|
|
|
case kStepToEnd:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &COnScreenVideoControl::DrawStepToEndButton)));
|
|
}
|
|
break;
|
|
case kStepToStart:
|
|
{
|
|
m_buttons[i].SetButtonDrawCallBack((MakeFunctor(*this, &COnScreenVideoControl::DrawStepToStartButton)));
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
COnScreenButton* COnScreenVideoControl::GetButton(const u32& button)
|
|
{
|
|
if(button < kMaxNumButtons)
|
|
{
|
|
return &m_buttons[button];
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
void COnScreenVideoControl::Process()
|
|
{
|
|
Vector3 points[4];
|
|
points[0].Set(m_screenExtents.GetMinX(), m_screenExtents.GetMinY(), 0.0f);
|
|
points[1].Set(m_screenExtents.GetMinX(), m_screenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(m_screenExtents.GetMaxX(), m_screenExtents.GetMaxY(), 0.0f);
|
|
points[3].Set(m_screenExtents.GetMaxX(), m_screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(points, 4, NULL, true, GetColor(kVideoControlBackgroundColor) );
|
|
|
|
Vector3 borderPoints[4];
|
|
borderPoints[0].Set(m_screenExtents.GetMinX(), m_screenExtents.GetMinY(), 0.0f);
|
|
borderPoints[1].Set(m_screenExtents.GetMinX(), m_screenExtents.GetMaxY(), 0.0f);
|
|
borderPoints[2].Set(m_screenExtents.GetMaxX(), m_screenExtents.GetMaxY(), 0.0f);
|
|
borderPoints[3].Set(m_screenExtents.GetMaxX(), m_screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(borderPoints, 4, NULL, false, GetColor(kVideoControlDisplayOutlineColor) );
|
|
|
|
for(int i =0; i < kMaxNumButtons; i++)
|
|
{
|
|
m_buttons[i].Update();
|
|
m_buttons[i].Draw();
|
|
}
|
|
|
|
}
|
|
|
|
// PURPOSE: Gets the colour of a particular element
|
|
Color32 COnScreenVideoControl::GetColor(eColorType type)
|
|
{
|
|
if(type < kMaxNumColors)
|
|
{
|
|
return m_colors[type];
|
|
}
|
|
|
|
return Color32(0,0,0,0);
|
|
}
|
|
|
|
void COnScreenVideoControl::SetCanvasSize(CScreenExtents& screenExtents)
|
|
{
|
|
TUNE_FLOAT(CanvasOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
screenExtents.Set(screenExtents.GetMinX() + CanvasOffset, screenExtents.GetMinY() + CanvasOffset, screenExtents.GetMaxX() - CanvasOffset, screenExtents.GetMaxY() - CanvasOffset);
|
|
}
|
|
|
|
void COnScreenVideoControl::DrawStepToStartButton(const CScreenExtents& screenExtents)
|
|
{
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
TUNE_FLOAT(borderOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(barwidthOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(firstArrowPecent, 0.56f, 0.0f, 5.0f, 0.01f)
|
|
TUNE_FLOAT(secondArrowPecent, 0.44f, 0.0f, 5.0f, 0.01f)
|
|
|
|
//vertical bar
|
|
Vector3 points[4];
|
|
points[0].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
points[1].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[2].Set(Canvas.GetMinX() + borderOffset + barwidthOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[3].Set(Canvas.GetMinX() + borderOffset + barwidthOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
|
|
Vector3 firstArrowpoints[3];
|
|
firstArrowpoints[0].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
firstArrowpoints[1].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
firstArrowpoints[2].Set(Canvas.GetMinX() + (Canvas.GetWidth() * firstArrowPecent), (Canvas.GetMinY() + borderOffset) + (((Canvas.GetMaxY() - borderOffset) - (Canvas.GetMinY() + borderOffset)) / 2.0f) , 0.0f);
|
|
|
|
Vector3 secondArrowpoints[3];
|
|
secondArrowpoints[0].Set(Canvas.GetMaxX() - (Canvas.GetWidth() * secondArrowPecent), Canvas.GetMinY() + borderOffset, 0.0f);
|
|
secondArrowpoints[1].Set(Canvas.GetMaxX() - (Canvas.GetWidth() * secondArrowPecent), Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
secondArrowpoints[2].Set(Canvas.GetMinX() + borderOffset + barwidthOffset, (Canvas.GetMinY() + borderOffset) + (((Canvas.GetMaxY() - borderOffset) - (Canvas.GetMinY() + borderOffset)) / 2.0f) , 0.0f);
|
|
|
|
if(DrawButtonBackground(Canvas, kStepToStart))
|
|
{
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStepToStart].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
grcDrawPolygon(firstArrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepToStart].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
grcDrawPolygon(secondArrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepToStart].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
}
|
|
else
|
|
{
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStepToStart].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
grcDrawPolygon(firstArrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepToStart].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
grcDrawPolygon(secondArrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepToStart].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
|
|
}
|
|
}
|
|
|
|
|
|
void COnScreenVideoControl::DrawStepBackwardsButton(const CScreenExtents& screenExtents)
|
|
{
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
TUNE_FLOAT(borderOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(barwidthOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
//vertical bar
|
|
Vector3 points[4];
|
|
points[0].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
points[1].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[2].Set(Canvas.GetMinX() + borderOffset + barwidthOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[3].Set(Canvas.GetMinX() + borderOffset + barwidthOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
|
|
Vector3 arrowpoints[3];
|
|
arrowpoints[0].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
arrowpoints[1].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
arrowpoints[2].Set(Canvas.GetMinX() + borderOffset + barwidthOffset, (Canvas.GetMinY() + borderOffset) + (((Canvas.GetMaxY() - borderOffset) - (Canvas.GetMinY() + borderOffset)) / 2.0f) , 0.0f);
|
|
|
|
if(DrawButtonBackground(Canvas, kStepBackwards))
|
|
{
|
|
grcDrawPolygon(arrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepBackwards].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStepBackwards].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
}
|
|
else
|
|
{
|
|
grcDrawPolygon(arrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepBackwards].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStepBackwards].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
}
|
|
}
|
|
|
|
void COnScreenVideoControl::DrawPlayForwardsButton(const CScreenExtents& screenExtents)
|
|
{
|
|
TUNE_FLOAT(borderOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
//draw an arrow
|
|
Vector3 points[3];
|
|
points[0].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
points[1].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[2].Set(Canvas.GetMaxX() - borderOffset, (Canvas.GetMinY() + borderOffset) + (((Canvas.GetMaxY() - borderOffset) - (Canvas.GetMinY() + borderOffset)) / 2.0f) , 0.0f);
|
|
|
|
if(DrawButtonBackground(Canvas, kPlayForwards))
|
|
{
|
|
grcDrawPolygon(points, 3, NULL, m_renderSolid, m_buttons[kPlayForwards].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
}
|
|
else
|
|
{
|
|
grcDrawPolygon(points, 3, NULL, m_renderSolid, m_buttons[kPlayForwards].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
}
|
|
|
|
}
|
|
|
|
void COnScreenVideoControl::DrawPlayBackwardsButton(const CScreenExtents& screenExtents)
|
|
{
|
|
TUNE_FLOAT(borderOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
//draw an arrow
|
|
Vector3 points[3];
|
|
points[0].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
points[1].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[2].Set(Canvas.GetMinX() + borderOffset, (Canvas.GetMinY() + borderOffset) + (((Canvas.GetMaxY() - borderOffset) - (Canvas.GetMinY() + borderOffset)) / 2.0f) , 0.0f);
|
|
|
|
if(DrawButtonBackground(Canvas, kPlayBackwards))
|
|
{
|
|
grcDrawPolygon(points, 3, NULL, m_renderSolid, m_buttons[kPlayBackwards].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
}
|
|
else
|
|
{
|
|
grcDrawPolygon(points, 3, NULL, m_renderSolid, m_buttons[kPlayBackwards].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
}
|
|
}
|
|
|
|
void COnScreenVideoControl::DrawStopButton(const CScreenExtents& screenExtents)
|
|
{
|
|
TUNE_FLOAT(borderOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
Vector3 points[4];
|
|
points[0].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
points[1].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[2].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[3].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
|
|
if(DrawButtonBackground(Canvas, kStop))
|
|
{
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStop].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
}
|
|
else
|
|
{
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStop].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
}
|
|
}
|
|
void COnScreenVideoControl::DrawStepForwardsButton(const CScreenExtents& screenExtents)
|
|
{
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
TUNE_FLOAT(borderOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(barwidthOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
|
|
//vertical bar
|
|
Vector3 points[4];
|
|
points[0].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
points[1].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[2].Set(Canvas.GetMaxX() - borderOffset - barwidthOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[3].Set(Canvas.GetMaxX() - borderOffset - barwidthOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
|
|
Vector3 arrowpoints[3];
|
|
arrowpoints[0].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
arrowpoints[1].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
arrowpoints[2].Set(Canvas.GetMaxX() - borderOffset - barwidthOffset, (Canvas.GetMinY() + borderOffset) + (((Canvas.GetMaxY() - borderOffset) - (Canvas.GetMinY() + borderOffset)) / 2.0f) , 0.0f);
|
|
|
|
if(DrawButtonBackground(Canvas, kStepForwards))
|
|
{
|
|
grcDrawPolygon(arrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepForwards].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStepForwards].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonColor));
|
|
}
|
|
else
|
|
{
|
|
grcDrawPolygon(arrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepForwards].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStepForwards].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
}
|
|
}
|
|
|
|
void COnScreenVideoControl::DrawStepToEndButton(const CScreenExtents& screenExtents)
|
|
{
|
|
CScreenExtents Canvas(screenExtents.GetMin(), screenExtents.GetMax());
|
|
SetCanvasSize(Canvas);
|
|
|
|
TUNE_FLOAT(borderOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(barwidthOffset, 2.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(firstArrowPecent, 0.56f, 0.0f, 5.0f, 0.01f)
|
|
TUNE_FLOAT(secondArrowPecent, 0.44f, 0.0f, 5.0f, 0.01f)
|
|
|
|
//vertical bar
|
|
Vector3 points[4];
|
|
points[0].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
points[1].Set(Canvas.GetMaxX() - borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[2].Set(Canvas.GetMaxX() - borderOffset - barwidthOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
points[3].Set(Canvas.GetMaxX() - borderOffset - barwidthOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
|
|
Vector3 firstArrowpoints[3];
|
|
firstArrowpoints[0].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMinY() + borderOffset, 0.0f);
|
|
firstArrowpoints[1].Set(Canvas.GetMinX() + borderOffset, Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
firstArrowpoints[2].Set(Canvas.GetMaxX() - (Canvas.GetWidth() * firstArrowPecent) , (Canvas.GetMinY() + borderOffset) + (((Canvas.GetMaxY() - borderOffset) - (Canvas.GetMinY() + borderOffset)) / 2.0f) , 0.0f);
|
|
|
|
|
|
Vector3 secondArrowpoints[3];
|
|
secondArrowpoints[0].Set(Canvas.GetMinX() + (Canvas.GetWidth() * secondArrowPecent), Canvas.GetMinY() + borderOffset, 0.0f);
|
|
secondArrowpoints[1].Set(Canvas.GetMinX() + (Canvas.GetWidth() * secondArrowPecent), Canvas.GetMaxY() - borderOffset, 0.0f);
|
|
secondArrowpoints[2].Set(Canvas.GetMaxX() - borderOffset - barwidthOffset, (Canvas.GetMinY() + borderOffset) + (((Canvas.GetMaxY() - borderOffset) - (Canvas.GetMinY() + borderOffset)) / 2.0f) , 0.0f);
|
|
|
|
|
|
if(DrawButtonBackground(Canvas, kStepToEnd))
|
|
{
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStepToEnd].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonHighLigtColor));
|
|
|
|
grcDrawPolygon(firstArrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepToEnd].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonHighLigtColor));
|
|
|
|
grcDrawPolygon(secondArrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepToEnd].IsHoveringOver() ? GetColor(kVideoControlActiveButtonHighLigtColor) : GetColor(kVideoControlActiveButtonHighLigtColor));
|
|
}
|
|
else
|
|
{
|
|
grcDrawPolygon(points, 4, NULL, m_renderSolid, m_buttons[kStepToEnd].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
|
|
grcDrawPolygon(firstArrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepToEnd].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
|
|
grcDrawPolygon(secondArrowpoints, 3, NULL, m_renderSolid, m_buttons[kStepToEnd].IsHoveringOver() ? GetColor(kVideoControlHoverButtonColor) : GetColor(kVideoControlButtonColor));
|
|
}
|
|
}
|
|
|
|
bool COnScreenVideoControl::DrawButtonBackground(const CScreenExtents& screenExtents, const u32& button)
|
|
{
|
|
if(m_buttons[button].WasPressed())
|
|
{
|
|
Vector3 outlinePoints[4];
|
|
outlinePoints[0].Set(screenExtents.GetMinX(), screenExtents.GetMinY(), 0.0f);
|
|
outlinePoints[1].Set(screenExtents.GetMinX(), screenExtents.GetMaxY(), 0.0f);
|
|
outlinePoints[2].Set(screenExtents.GetMaxX(), screenExtents.GetMaxY(), 0.0f);
|
|
outlinePoints[3].Set(screenExtents.GetMaxX(), screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(outlinePoints, 4, NULL, false, GetColor(kVideoControlPanelButtonOutlineColor) );
|
|
}
|
|
|
|
if(m_buttons[button].IsActive() || m_buttons[button].IsHeld())
|
|
{
|
|
Vector3 bgpoints[4];
|
|
bgpoints[0].Set(screenExtents.GetMinX(), screenExtents.GetMinY(), 0.0f);
|
|
bgpoints[1].Set(screenExtents.GetMinX(), screenExtents.GetMaxY(), 0.0f);
|
|
bgpoints[2].Set(screenExtents.GetMaxX(), screenExtents.GetMaxY(), 0.0f);
|
|
bgpoints[3].Set(screenExtents.GetMaxX(), screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(bgpoints, 4, NULL, true, GetColor(kVideoControlActiveButtonBackgroundColor) );
|
|
|
|
Vector3 outlinePoints[4];
|
|
outlinePoints[0].Set(screenExtents.GetMinX(), screenExtents.GetMinY(), 0.0f);
|
|
outlinePoints[1].Set(screenExtents.GetMinX(), screenExtents.GetMaxY(), 0.0f);
|
|
outlinePoints[2].Set(screenExtents.GetMaxX(), screenExtents.GetMaxY(), 0.0f);
|
|
outlinePoints[3].Set(screenExtents.GetMaxX(), screenExtents.GetMinY(), 0.0f);
|
|
|
|
grcDrawPolygon(outlinePoints, 4, NULL, false, GetColor(kVideoControlPanelActiveButtonOutlineColor) );
|
|
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
CEventPanel::CEventPanel(EventInfo info)
|
|
:m_event(info)
|
|
,m_eventHeight(10.0f)
|
|
,m_offscreenArrowMarker(5.0f)
|
|
{
|
|
}
|
|
|
|
CEventPanel::~CEventPanel()
|
|
{
|
|
}
|
|
|
|
void CEventPanel::RenderToolsOverlay(CAnimSceneEditor* animSceneEditor, CScreenExtents& GroupSceenExtents, CEventPanelGroup* PanelGroup, int colourId)
|
|
{
|
|
if(m_event.event)
|
|
{
|
|
RenderEventToolsOverlay(animSceneEditor, m_event, GroupSceenExtents, PanelGroup, colourId);
|
|
}
|
|
}
|
|
|
|
//Render the blend in/out markers
|
|
void CEventPanel::RenderEventToolsOverlay(CAnimSceneEditor* animSceneEditor, EventInfo& info, CScreenExtents& GroupSceenExtents, CEventPanelGroup* PanelGroup, int colourId)
|
|
{
|
|
static float s_boldLineSize = 1.f;
|
|
static float s_minTagWidth = 2.0f;
|
|
|
|
CAnimSceneEvent* evt = info.event;
|
|
if (evt)
|
|
{
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Get screen space information for the event
|
|
//////////////////////////////////////////////////////////////////////////
|
|
float startX = animSceneEditor->GetTimeLine().GetScreenX(evt->GetStart());
|
|
float endX = animSceneEditor->GetTimeLine().GetScreenX(evt->GetEnd());
|
|
float blendInStartX = animSceneEditor->GetTimeLine().GetScreenX(evt->GetStart());
|
|
|
|
//float groupSpacing = PanelGroup->GetGroupSpacing();
|
|
bool endXPastRight = false; bool startXPastLeft = false;
|
|
float arrowSize = Clamp(PanelGroup->GetGroupHeight() / 8.0f, 1.5f, 5.0f);
|
|
|
|
//Handle colour when selected
|
|
Color32 eventColor;
|
|
evt->GetEditorColor(eventColor, *animSceneEditor, colourId);
|
|
bool isSelected = (evt==animSceneEditor->GetSelectedEvent());
|
|
if(isSelected)
|
|
{
|
|
eventColor = animSceneEditor->GetColor(CAnimSceneEditor::kSelectedEventMarkerColor);
|
|
}
|
|
eventColor.SetAlpha(255);
|
|
|
|
//Detect event extents being off the drawable area
|
|
if(endX > GroupSceenExtents.GetMaxX())
|
|
{
|
|
endXPastRight = true;
|
|
}
|
|
|
|
if(startX < GroupSceenExtents.GetMinX())
|
|
{
|
|
startXPastLeft = true;
|
|
}
|
|
|
|
// Get the blend in and out information
|
|
bool hasBlendIn = false; float blendInDuration = 0.f; float blendInEndX = 0.f;
|
|
bool hasBlendOut = false;float blendOutDuration = 0.f; float blendOutEndX = 0.f;
|
|
if(evt->GetType() == AnimSceneEventType::PlayAnimEvent)
|
|
{
|
|
CAnimScenePlayAnimEvent* evtPA = static_cast<CAnimScenePlayAnimEvent*>(evt);
|
|
blendInDuration = evtPA->GetPoseBlendInDuration();
|
|
blendOutDuration = evtPA->GetPoseBlendOutDuration();
|
|
if(blendInDuration > 0.f)
|
|
{
|
|
hasBlendIn = true;
|
|
blendInEndX = animSceneEditor->GetTimeLine().GetScreenX(blendInDuration + evtPA->GetStart());
|
|
if(blendInEndX < GroupSceenExtents.GetMinX())
|
|
{
|
|
hasBlendIn = false;
|
|
}
|
|
}
|
|
if(blendOutDuration > 0.f)
|
|
{
|
|
hasBlendOut = true;
|
|
blendOutEndX = animSceneEditor->GetTimeLine().GetScreenX(blendOutDuration + evtPA->GetEnd());
|
|
if(blendOutEndX < endX || blendOutEndX < GroupSceenExtents.GetMinX())
|
|
{
|
|
hasBlendOut = false;
|
|
}
|
|
}
|
|
}//end if(evt->GetType() == AnimSceneEventType::PlayAnimEvent)
|
|
//Camera blending support
|
|
if(evt->GetType() == AnimSceneEventType::PlayCameraAnimEvent)
|
|
{
|
|
CAnimScenePlayCameraAnimEvent* evtPA = static_cast<CAnimScenePlayCameraAnimEvent*>(evt);
|
|
blendInDuration = evtPA->GetBlendInDuration();
|
|
blendOutDuration = evtPA->GetBlendOutDuration();
|
|
if(blendInDuration > 0.f)
|
|
{
|
|
hasBlendIn = true;
|
|
blendInEndX = animSceneEditor->GetTimeLine().GetScreenX(blendInDuration + evtPA->GetStart());
|
|
if(blendInEndX < GroupSceenExtents.GetMinX())
|
|
{
|
|
hasBlendIn = false;
|
|
}
|
|
}
|
|
if(blendOutDuration > 0.f)
|
|
{
|
|
hasBlendOut = true;
|
|
blendOutEndX = animSceneEditor->GetTimeLine().GetScreenX(blendOutDuration + evtPA->GetEnd());
|
|
if(blendOutEndX < endX || blendOutEndX < GroupSceenExtents.GetMinX())
|
|
{
|
|
hasBlendOut = false;
|
|
}
|
|
}
|
|
}
|
|
|
|
// bail for events offscreen, and handle their blendouts
|
|
if (endX < GroupSceenExtents.GetMinX())
|
|
{
|
|
if(hasBlendOut)
|
|
{
|
|
//calculate intersection of line from bottom of event start to final location
|
|
Vector3 blendStart(endX, GroupSceenExtents.GetMaxY(), 0.0f);
|
|
Vector3 blendEnd(blendOutEndX,GroupSceenExtents.GetMinY(), 0.0f);
|
|
|
|
//y = mx + c
|
|
//computing m
|
|
float xdiff = endX - blendOutEndX;
|
|
float ydiff = GroupSceenExtents.GetMaxY() - GroupSceenExtents.GetMinY();
|
|
float m = ydiff / xdiff;
|
|
//c = y - mx
|
|
float c = GroupSceenExtents.GetMaxY() - m*endX;
|
|
//y value at point
|
|
float blendOutStartY = m*GroupSceenExtents.GetMinX() + c;
|
|
|
|
//Draw white background triangle
|
|
Color32 boColour = animSceneEditor->GetColor(CAnimSceneEditor::kEventBackgroundColor);
|
|
boColour.SetAlpha((int) (CAnimSceneEditor::ms_editorSettingBackgroundAlpha*255));
|
|
Vector3 points[4]; //buffer for (up to 4 point) polygons
|
|
points[0].Set(GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMinY(), 0.0f);//top left
|
|
points[1].Set(blendOutEndX, GroupSceenExtents.GetMinY(), 0.0f);//Arrow past right of event
|
|
points[2].Set(GroupSceenExtents.GetMinX(), blendOutStartY, 0.0f);//bottom left
|
|
grcDrawPolygon(points, 3, NULL, true, boColour);
|
|
|
|
//Draw coloured line indicating blend amount
|
|
if(CAnimSceneEditor::ms_editorSettingUseEventColourForMarker)
|
|
{
|
|
boColour = eventColor;
|
|
}
|
|
else
|
|
{
|
|
boColour = animSceneEditor->GetColor(CAnimSceneEditor::kBlendOutMarkerColor);
|
|
}
|
|
boColour.SetAlpha(255);
|
|
grcDrawLine(points[1],points[2],boColour,boColour);
|
|
|
|
//Coloured line along the top
|
|
points[0].Set(GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMinY(), 0.0f);//top right upper
|
|
points[1].Set(blendOutEndX, GroupSceenExtents.GetMinY(), 0.0f);//Arrow past right of event (up and to the right) upper
|
|
points[2].Set(blendOutEndX, GroupSceenExtents.GetMinY() - s_boldLineSize, 0.0f);//Arrow past right of event (up and to the right) lower
|
|
points[3].Set(GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMinY() - s_boldLineSize, 0.0f);//bottom left
|
|
grcDrawPolygon(points, 4, NULL, TRUE, boColour);
|
|
|
|
//Coloured Triangle (denoting end of blend out)
|
|
points[0].Set(blendOutEndX - 3*arrowSize, GroupSceenExtents.GetMinY(), 0.0f);
|
|
points[1].Set(blendOutEndX + 3*arrowSize, GroupSceenExtents.GetMinY(), 0.0f);
|
|
points[2].Set(blendOutEndX, GroupSceenExtents.GetMinY() + 3*arrowSize, 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, TRUE, boColour);
|
|
|
|
//Draw a dashed line under the block to indicate final clip length
|
|
points[0].Set(blendOutEndX, GroupSceenExtents.GetMinY(),0.f);
|
|
points[1].Set(blendOutEndX, GroupSceenExtents.GetMaxY(),0);
|
|
DrawDashedLine(points[0],points[1],boColour,5);
|
|
}
|
|
return;
|
|
}
|
|
|
|
// Ignore drawing of tools if off the end of the right hand side of the screen
|
|
if (startX > GroupSceenExtents.GetMaxX())
|
|
{
|
|
return;
|
|
}
|
|
|
|
// Clamp to drawable range
|
|
startX = Clamp(startX, GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMaxX());
|
|
endX = Clamp(endX, GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMaxX());
|
|
CScreenExtents EventScreenExtents(startX, GroupSceenExtents.GetMinY(), endX, GroupSceenExtents.GetMaxY());
|
|
|
|
bool isDurationless = false;
|
|
|
|
// make sure there's always at least a thin line
|
|
if (endX - startX<s_minTagWidth)
|
|
{
|
|
isDurationless = true;
|
|
endX = startX + s_minTagWidth;
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
/// Properties
|
|
//////////////////////////////////////////////////////////////////////////
|
|
float mouseX = static_cast<float>(ioMouse::GetX());
|
|
float mouseY = static_cast<float>(ioMouse::GetY());
|
|
bool hoveringEvent = EventScreenExtents.Contains(mouseX, mouseY);
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render
|
|
//////////////////////////////////////////////////////////////////////////
|
|
Vector3 points[4];
|
|
eventColor.SetAlpha(255);
|
|
|
|
if (hoveringEvent && !isSelected)
|
|
{
|
|
eventColor.SetRed(Clamp(eventColor.GetRed() + 25, 0, 255));
|
|
eventColor.SetBlue(Clamp(eventColor.GetBlue() + 25, 0, 255));
|
|
eventColor.SetGreen(Clamp(eventColor.GetGreen() + 25, 0, 255));
|
|
}
|
|
|
|
//Draw blend in - white triangles, coloured ramps and indicators
|
|
//There is an assumption that a blend will not go across the whole timeline here.
|
|
if(hasBlendIn)
|
|
{
|
|
Color32 biColour = animSceneEditor->GetColor(CAnimSceneEditor::kEventBackgroundColor);
|
|
biColour.SetAlpha((int) (CAnimSceneEditor::ms_editorSettingBackgroundAlpha*255) );
|
|
//Handle being only partially in the scene (left side)
|
|
if(blendInStartX < GroupSceenExtents.GetMinX())
|
|
{
|
|
//Line equation: y = mx + c
|
|
//computing m
|
|
float xdiff = blendInStartX - blendInEndX;
|
|
float ydiff = GroupSceenExtents.GetMaxY() - GroupSceenExtents.GetMinY();
|
|
float m = ydiff / xdiff;
|
|
//c = y - mx
|
|
float c = GroupSceenExtents.GetMaxY() - m*blendInStartX;
|
|
//y value at point
|
|
float blendInStartY = m*GroupSceenExtents.GetMinX() + c;
|
|
|
|
//Draw blend in partial triangle
|
|
Vector3 points[4];
|
|
points[0].Set(GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMaxY(), 0.0f);//bottom left
|
|
points[1].Set(GroupSceenExtents.GetMinX(),blendInStartY, 0.0f);//start height
|
|
points[2].Set(blendInEndX, GroupSceenExtents.GetMinY(), 0.0f);//start of fully blended in
|
|
points[3].Set(blendInEndX, GroupSceenExtents.GetMaxY(), 0.0f);//bottom right
|
|
grcDrawPolygon(points, 4, NULL, true,biColour);
|
|
if(!CAnimSceneEditor::ms_editorSettingUseEventColourForMarker)
|
|
{
|
|
biColour = animSceneEditor->GetColor(CAnimSceneEditor::kBlendInMarkerColor);
|
|
}
|
|
else
|
|
{
|
|
biColour = eventColor;
|
|
}
|
|
//Draw coloured blend amount
|
|
grcDrawLine(points[1],points[2],biColour,biColour);
|
|
|
|
|
|
if(!CAnimSceneEditor::ms_editorSettingUseEventColourForMarker)
|
|
{
|
|
biColour = animSceneEditor->GetColor(CAnimSceneEditor::kBlendInMarkerColor);
|
|
}
|
|
biColour.SetAlpha(255);
|
|
|
|
//Along the bottom
|
|
points[0].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY(), 0.0f);//top left upper
|
|
points[1].Set(blendInEndX, EventScreenExtents.GetMaxY(), 0.0f);//Arrow past right of event (up and to the right) upper
|
|
points[2].Set(blendInEndX, EventScreenExtents.GetMaxY() + s_boldLineSize, 0.0f);//Arrow past right of event (up and to the right) lower
|
|
points[3].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY() + s_boldLineSize, 0.0f);//bottom left
|
|
grcDrawPolygon(points, 4, NULL, TRUE,biColour);
|
|
|
|
//Upward line
|
|
points[0].Set(blendInEndX - s_boldLineSize/2.0f, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(blendInEndX - s_boldLineSize/2.0f, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[2].Set(blendInEndX + s_boldLineSize/2.0f, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[3].Set(blendInEndX + s_boldLineSize/2.0f, EventScreenExtents.GetMaxY(), 0.0f);
|
|
grcDrawPolygon(points, 4, NULL, TRUE, biColour);
|
|
//Draw an arrow pointing up
|
|
points[0].Set(blendInEndX - 3*arrowSize, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(blendInEndX + 3*arrowSize, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(blendInEndX, EventScreenExtents.GetMaxY() - 3*arrowSize, 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, TRUE, biColour);
|
|
}
|
|
else if(blendInStartX < GroupSceenExtents.GetMaxX() && blendInEndX > GroupSceenExtents.GetMaxX()) // Check whether we are off the right hand side of the screen
|
|
{
|
|
//Line equation: y = mx + c
|
|
//computing m
|
|
float xdiff = blendInStartX - blendInEndX;
|
|
float ydiff = GroupSceenExtents.GetMaxY() - GroupSceenExtents.GetMinY();
|
|
float m = ydiff / xdiff;
|
|
//c = y - mx
|
|
float c = GroupSceenExtents.GetMaxY() - m*blendInStartX;
|
|
//y value at point
|
|
float blendInEndY = m*GroupSceenExtents.GetMaxX() + c;
|
|
|
|
//Draw blend in partial triangle
|
|
points[0].Set(blendInStartX, GroupSceenExtents.GetMaxY(), 0.0f);//bottom left
|
|
points[1].Set(GroupSceenExtents.GetMaxX(),GroupSceenExtents.GetMaxY(), 0.0f);//bottom right
|
|
points[2].Set(GroupSceenExtents.GetMaxX(), blendInEndY, 0.0f);//point of intersection with end of screen
|
|
grcDrawPolygon(points, 3, NULL, true,biColour);
|
|
if(!CAnimSceneEditor::ms_editorSettingUseEventColourForMarker)
|
|
{
|
|
biColour = animSceneEditor->GetColor(CAnimSceneEditor::kBlendInMarkerColor);
|
|
}
|
|
else
|
|
{
|
|
biColour = eventColor;
|
|
}
|
|
biColour.SetAlpha(255);
|
|
//Draw coloured blend amount
|
|
grcDrawLine(points[0],points[2],biColour,biColour);
|
|
|
|
//Along the bottom (clipped at end)
|
|
points[0].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(GroupSceenExtents.GetMaxX(), EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(GroupSceenExtents.GetMaxX(), EventScreenExtents.GetMaxY() + s_boldLineSize, 0.0f);
|
|
points[3].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY() + s_boldLineSize, 0.0f);
|
|
grcDrawPolygon(points, 4, NULL, TRUE,biColour);
|
|
//Triangle (beginning)
|
|
points[0].Set(EventScreenExtents.GetMinX() - 3*arrowSize, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(EventScreenExtents.GetMinX() + 3*arrowSize, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY() - 3*arrowSize, 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, TRUE, biColour);
|
|
//Draw a 'background' coloured line over the line that already exists (from even block rendering) to make it dashed.
|
|
points[0].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMinY(),0.f);
|
|
points[1].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY(),0.f);
|
|
DrawDashedLine(points[0],points[1],animSceneEditor->GetColor(CAnimSceneEditor::kEventBackgroundColor),5);
|
|
}
|
|
else // The blend indicator is entirely within the display area
|
|
{
|
|
points[0].Set(blendInEndX, EventScreenExtents.GetMaxY(), 0.0f);//top left
|
|
points[1].Set(blendInEndX, EventScreenExtents.GetMinY(), 0.0f);//bottom left
|
|
points[2].Set(blendInStartX, EventScreenExtents.GetMaxY(), 0.0f);//Arrow INSIDE left of event on top
|
|
grcDrawPolygon(points, 3, NULL, true,biColour);
|
|
|
|
if(!CAnimSceneEditor::ms_editorSettingUseEventColourForMarker)
|
|
{
|
|
biColour = animSceneEditor->GetColor(CAnimSceneEditor::kBlendInMarkerColor);
|
|
}
|
|
else
|
|
{
|
|
biColour = eventColor;
|
|
}
|
|
grcDrawLine(points[1],points[2],biColour,biColour);
|
|
|
|
//Triangle pointing upwards (beginning)
|
|
points[0].Set(EventScreenExtents.GetMinX() - 3*arrowSize, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(EventScreenExtents.GetMinX() + 3*arrowSize, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY() - 3*arrowSize, 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, TRUE, biColour);
|
|
//Draw a 'background' coloured line over the line that already exists (from even block rendering) to make it dashed.
|
|
points[0].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMinY(),0.f);
|
|
points[1].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY(),0.f);
|
|
DrawDashedLine(points[0],points[1],animSceneEditor->GetColor(CAnimSceneEditor::kEventBackgroundColor),5);
|
|
|
|
if(!CAnimSceneEditor::ms_editorSettingUseEventColourForMarker)
|
|
{
|
|
biColour = animSceneEditor->GetColor(CAnimSceneEditor::kBlendInMarkerColor);
|
|
}
|
|
biColour.SetAlpha(255);
|
|
|
|
//Along the bottom
|
|
points[0].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(blendInEndX, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(blendInEndX, EventScreenExtents.GetMaxY() + s_boldLineSize, 0.0f);
|
|
points[3].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY() + s_boldLineSize, 0.0f);
|
|
grcDrawPolygon(points, 4, NULL, TRUE,biColour);
|
|
//Upward line at end
|
|
points[0].Set(blendInEndX - s_boldLineSize/2.0f, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(blendInEndX - s_boldLineSize/2.0f, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[2].Set(blendInEndX + s_boldLineSize/2.0f, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[3].Set(blendInEndX + s_boldLineSize/2.0f, EventScreenExtents.GetMaxY(), 0.0f);
|
|
grcDrawPolygon(points, 4, NULL, TRUE, biColour);
|
|
//Draw an arrow pointing up at end
|
|
points[0].Set(blendInEndX - 3*arrowSize, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(blendInEndX + 3*arrowSize, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(blendInEndX, EventScreenExtents.GetMaxY() - 3*arrowSize, 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, TRUE, biColour);
|
|
}
|
|
|
|
|
|
}//end has blend in
|
|
|
|
//Draw blend out (if in range)
|
|
if(hasBlendOut && !endXPastRight)
|
|
{
|
|
Color32 boColour = animSceneEditor->GetColor(CAnimSceneEditor::kEventBackgroundColor);
|
|
boColour.SetAlpha( (int) (CAnimSceneEditor::ms_editorSettingBackgroundAlpha*255) );
|
|
|
|
//Handle being only partially in the scene
|
|
if(blendOutEndX > GroupSceenExtents.GetMaxX())
|
|
{
|
|
//Line equation: y = mx + c
|
|
//computing m
|
|
float xdiff = EventScreenExtents.GetMaxX() - blendOutEndX;
|
|
float ydiff = GroupSceenExtents.GetMaxY() - GroupSceenExtents.GetMinY();
|
|
float m = ydiff / xdiff;
|
|
//c = y - mx
|
|
float c = GroupSceenExtents.GetMaxY() - m*EventScreenExtents.GetMaxX();
|
|
//y value at point
|
|
float blendOutEndY = m*GroupSceenExtents.GetMaxX() + c;
|
|
|
|
//Draw blend out partial triangle
|
|
points[0].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY(), 0.0f);//top right
|
|
points[1].Set(GroupSceenExtents.GetMaxX(), EventScreenExtents.GetMinY(), 0.0f);//Arrow past right of event
|
|
points[2].Set(GroupSceenExtents.GetMaxX(), blendOutEndY, 0.0f);//Arrow past right of event//Arrow lower past right of event
|
|
points[3].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMaxY(), 0.0f);//bottom right
|
|
grcDrawPolygon(points, 4, NULL, true,boColour);
|
|
|
|
if(!CAnimSceneEditor::ms_editorSettingUseEventColourForMarker)
|
|
{
|
|
boColour = animSceneEditor->GetColor(CAnimSceneEditor::kBlendOutMarkerColor);
|
|
}
|
|
else
|
|
{
|
|
boColour = eventColor;
|
|
}
|
|
boColour.SetAlpha(255);
|
|
//Draw the line representing the blend amount
|
|
grcDrawLine(points[2],points[3],boColour,boColour);
|
|
|
|
// draw line along the top
|
|
points[0].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY(), 0.0f);//top right upper
|
|
points[1].Set(GroupSceenExtents.GetMaxX(), EventScreenExtents.GetMinY(), 0.0f);//Arrow past right of event (up and to the right) upper
|
|
points[2].Set(GroupSceenExtents.GetMaxX(), EventScreenExtents.GetMinY() - s_boldLineSize, 0.0f);//Arrow past right of event (up and to the right) lower
|
|
points[3].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY() - s_boldLineSize, 0.0f);//bottom left
|
|
grcDrawPolygon(points, 4, NULL, TRUE,boColour);
|
|
}
|
|
else // The blend indicator is entirely within the display area
|
|
{
|
|
//Draw blend out triangle
|
|
points[0].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMaxY(), 0.0f);//top right
|
|
points[1].Set(blendOutEndX, EventScreenExtents.GetMinY(), 0.0f);//Arrow past right of event
|
|
points[2].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY(), 0.0f);//bottom right
|
|
grcDrawPolygon(points, 3, NULL, true,boColour);
|
|
|
|
if(!CAnimSceneEditor::ms_editorSettingUseEventColourForMarker)
|
|
{
|
|
boColour = animSceneEditor->GetColor(CAnimSceneEditor::kBlendOutMarkerColor);
|
|
}
|
|
else
|
|
{
|
|
boColour = eventColor;
|
|
}
|
|
boColour.SetAlpha(255);
|
|
//Draw the line representing the blend amount
|
|
grcDrawLine(points[0],points[1],boColour,boColour);
|
|
|
|
// draw line along the top
|
|
points[0].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY(), 0.0f);//top right upper
|
|
points[1].Set(blendOutEndX, EventScreenExtents.GetMinY(), 0.0f);//Arrow past right of event (up and to the right) upper
|
|
points[2].Set(blendOutEndX, EventScreenExtents.GetMinY() - s_boldLineSize, 0.0f);//Arrow past right of event (up and to the right) lower
|
|
points[3].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY() - s_boldLineSize, 0.0f);//bottom left
|
|
grcDrawPolygon(points, 4, NULL, TRUE,boColour);
|
|
|
|
//Triangle (end)
|
|
points[0].Set(blendOutEndX - 3*arrowSize, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[1].Set(blendOutEndX + 3*arrowSize, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[2].Set(blendOutEndX, EventScreenExtents.GetMinY() + 3*arrowSize, 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, TRUE,boColour);
|
|
|
|
//Draw a dashed line under the block
|
|
points[0].Set(blendOutEndX, EventScreenExtents.GetMinY(),0.f);
|
|
points[1].Set(blendOutEndX, EventScreenExtents.GetMaxY(),0.f);
|
|
DrawDashedLine(points[0],points[1],boColour,5);
|
|
}
|
|
|
|
//Upward line
|
|
points[0].Set(EventScreenExtents.GetMaxX() + s_boldLineSize/2.0f, EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(EventScreenExtents.GetMaxX() + s_boldLineSize/2.0f, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[2].Set(EventScreenExtents.GetMaxX() - s_boldLineSize/2.0f, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[3].Set(EventScreenExtents.GetMaxX() - s_boldLineSize/2.0f, EventScreenExtents.GetMaxY(), 0.0f);
|
|
grcDrawPolygon(points, 4, NULL, TRUE,boColour);
|
|
|
|
//draw an arrow pointing down
|
|
points[0].Set(EventScreenExtents.GetMaxX() - 3*arrowSize, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[1].Set(EventScreenExtents.GetMaxX() + 3*arrowSize, EventScreenExtents.GetMinY(), 0.0f);
|
|
points[2].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY() + 3*arrowSize, 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, TRUE,boColour);
|
|
}//end has blend out
|
|
}
|
|
}
|
|
|
|
|
|
void CEventPanel::Render(CAnimSceneEditor* animSceneEditor, CScreenExtents& GroupSceenExtents, CEventPanelGroup* PanelGroup, int colourId)
|
|
{
|
|
if(m_event.event)
|
|
{
|
|
RenderEvent(animSceneEditor, m_event, GroupSceenExtents, PanelGroup, colourId);
|
|
}
|
|
}
|
|
|
|
void CEventPanel::RenderEvent(CAnimSceneEditor* animSceneEditor, EventInfo& info, CScreenExtents& GroupSceenExtents, CEventPanelGroup* PanelGroup, int colourId)
|
|
{
|
|
TUNE_FLOAT(ScreenPos, 0.0f, 0.0f, 10000.0f, 1.0f)
|
|
TUNE_FLOAT(eventHeightOffset, 12.0f, 0.0f, 10000.0f, 1.0f)
|
|
|
|
float eventHeight = GetTextHeight() + eventHeightOffset;
|
|
CAnimSceneEvent* evt = info.event;
|
|
|
|
if (evt)
|
|
{
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Get screen space information for the event
|
|
//////////////////////////////////////////////////////////////////////////
|
|
float startX = animSceneEditor->GetTimeLine().GetScreenX(evt->GetStart()) ;
|
|
float endX = animSceneEditor->GetTimeLine().GetScreenX(evt->GetEnd()) ;
|
|
//float currentTimeX = animSceneEditor->GetTimeLine().GetScreenX(animSceneEditor->GetScene()->GetTime());
|
|
float startFullyInX = animSceneEditor->GetTimeLine().GetScreenX(evt->GetStart());
|
|
float endFullyOutX = endX;
|
|
|
|
m_eventHeight = eventHeight;
|
|
|
|
//Check the start time if there is a blend
|
|
if(evt->GetType() == AnimSceneEventType::PlayAnimEvent)
|
|
{
|
|
CAnimScenePlayAnimEvent* evtPA = static_cast<CAnimScenePlayAnimEvent*>(evt);
|
|
startFullyInX = animSceneEditor->GetTimeLine().GetScreenX(evtPA->GetStartFullBlendInTime());
|
|
endFullyOutX = animSceneEditor->GetTimeLine().GetScreenX(evtPA->GetPoseBlendOutDuration() + evtPA->GetEnd());
|
|
}
|
|
//Camera blending support
|
|
if(evt->GetType() == AnimSceneEventType::PlayCameraAnimEvent)
|
|
{
|
|
CAnimScenePlayCameraAnimEvent* evtPA = static_cast<CAnimScenePlayCameraAnimEvent*>(evt);
|
|
startFullyInX = animSceneEditor->GetTimeLine().GetScreenX(evtPA->GetBlendInDuration() + evtPA->GetStart());
|
|
//Act like play anim events
|
|
endFullyOutX = animSceneEditor->GetTimeLine().GetScreenX(evtPA->GetEnd() + evtPA->GetBlendOutDuration());
|
|
endX = animSceneEditor->GetTimeLine().GetScreenX(evtPA->GetEnd());
|
|
}
|
|
Color32 eventColor;
|
|
evt->GetEditorColor(eventColor, *animSceneEditor, colourId);
|
|
eventColor.SetAlpha(255);
|
|
|
|
// bail for events offscreen
|
|
if (endFullyOutX < GroupSceenExtents.GetMinX())
|
|
{
|
|
return;
|
|
}
|
|
|
|
if (startX > GroupSceenExtents.GetMaxX())
|
|
{
|
|
return;
|
|
}
|
|
|
|
bool drawStartArrow = startX<GroupSceenExtents.GetMinX();
|
|
bool drawEndArrow = endFullyOutX>GroupSceenExtents.GetMaxX();
|
|
bool endXPastRight = false; bool endXPastLeft = false;
|
|
bool startFullyInXPastRight = false;
|
|
|
|
if(endX > GroupSceenExtents.GetMaxX())
|
|
{
|
|
endXPastRight = true;
|
|
}
|
|
if(endX < GroupSceenExtents.GetMinX())
|
|
{
|
|
endXPastLeft = true;
|
|
}
|
|
|
|
if(startFullyInX > GroupSceenExtents.GetMaxX())
|
|
{
|
|
startFullyInXPastRight = true;
|
|
}
|
|
|
|
startX = Clamp(startFullyInX, GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMaxX());
|
|
endX = Clamp(endX, GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMaxX());
|
|
|
|
CScreenExtents EventScreenExtents(startX, GroupSceenExtents.GetMinY(), endX, GroupSceenExtents.GetMaxY());
|
|
|
|
static float s_minTagWidth = 2.0f;
|
|
bool isDurationless = false;
|
|
|
|
// make sure there's always at least a thin line
|
|
if (endX - startX<s_minTagWidth)
|
|
{
|
|
isDurationless = true;
|
|
endX = startX + s_minTagWidth;
|
|
}
|
|
|
|
static float s_markerBoxSize = 3.0f;
|
|
static float s_preloadBoxSize = 3.0f;
|
|
static float s_preloadYOffset = 1.0f;
|
|
|
|
float preloadLength = Min(evt->GetPreloadDuration(), startX-GroupSceenExtents.GetMinX());
|
|
float preloadX = Max(animSceneEditor->GetTimeLine().GetScreenX(evt->GetPreloadStart()), GroupSceenExtents.GetMinX());
|
|
float preloadY = GroupSceenExtents.GetMaxY()+s_preloadYOffset;
|
|
|
|
//Compute blendin/out info
|
|
bool hasBlendIn = false; float blendInDuration = 0.f; float blendInStartX = 0.f;
|
|
bool hasBlendOut = false;float blendOutDuration = 0.f; float blendOutEndX = 0.f;
|
|
if(evt->GetType() == AnimSceneEventType::PlayAnimEvent)
|
|
{
|
|
CAnimScenePlayAnimEvent* evtPA = static_cast<CAnimScenePlayAnimEvent*>(evt);
|
|
blendInDuration = evtPA->GetPoseBlendInDuration();
|
|
blendOutDuration = evtPA->GetPoseBlendOutDuration();
|
|
|
|
if(blendInDuration > 0.f)
|
|
{
|
|
hasBlendIn = true;
|
|
if(startFullyInX < EventScreenExtents.GetMinX())
|
|
{
|
|
hasBlendIn = false;
|
|
}
|
|
blendInStartX = animSceneEditor->GetTimeLine().GetScreenX(evtPA->GetStart());
|
|
}
|
|
if(blendOutDuration > 0.f)
|
|
{
|
|
hasBlendOut = true;
|
|
blendOutEndX = animSceneEditor->GetTimeLine().GetScreenX(blendOutDuration + evtPA->GetEnd());
|
|
if(blendOutEndX < endX)
|
|
{
|
|
hasBlendOut = false;
|
|
}
|
|
}
|
|
}//end if(evt->GetType() == AnimSceneEventType::PlayAnimEvent)
|
|
//Camera blending support
|
|
if(evt->GetType() == AnimSceneEventType::PlayCameraAnimEvent)
|
|
{
|
|
CAnimScenePlayCameraAnimEvent* evtPA = static_cast<CAnimScenePlayCameraAnimEvent*>(evt);
|
|
blendInDuration = evtPA->GetBlendInDuration();
|
|
blendOutDuration = evtPA->GetBlendOutDuration();
|
|
if(blendInDuration > 0.f)
|
|
{
|
|
hasBlendIn = true;
|
|
if(startFullyInX < EventScreenExtents.GetMinX())
|
|
{
|
|
hasBlendIn = false;
|
|
}
|
|
}
|
|
if(blendOutDuration > 0.f)
|
|
{
|
|
hasBlendOut = true;
|
|
//act like playanim event
|
|
blendOutEndX = animSceneEditor->GetTimeLine().GetScreenX(blendOutDuration + evtPA->GetEnd());
|
|
if(blendOutEndX < endX)
|
|
{
|
|
hasBlendOut = false;
|
|
}
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Update
|
|
//////////////////////////////////////////////////////////////////////////
|
|
float mouseX = static_cast<float>(ioMouse::GetX());
|
|
float mouseY = static_cast<float>(ioMouse::GetY());
|
|
bool hoveringEvent = EventScreenExtents.Contains(mouseX, mouseY);
|
|
bool hoveringMarker = isDurationless && (Abs(mouseX - startX)<s_markerBoxSize) && (Abs(mouseY - GroupSceenExtents.GetMinY())<s_markerBoxSize);
|
|
|
|
if (!animSceneEditor->IsDragging())
|
|
{
|
|
bool leftMouseDown = ioMouse::GetButtons() & ioMouse::MOUSE_LEFT;
|
|
bool leftMousePressed = ioMouse::GetPressedButtons() & ioMouse::MOUSE_LEFT;
|
|
|
|
if (leftMouseDown)
|
|
{
|
|
static float s_edgeSelectTolerance = 3.0f;
|
|
|
|
bool hoveringEventStart = hoveringEvent && (Abs(mouseX - startX)<s_edgeSelectTolerance);
|
|
bool hoveringEventEnd = hoveringEvent && (Abs(mouseX - endX)<s_edgeSelectTolerance);
|
|
bool hoveringPreload = animSceneEditor->GetEditEventPreloads() && (Abs(mouseX - preloadX)<s_preloadBoxSize) && (Abs(mouseY - preloadY)<s_preloadBoxSize);
|
|
|
|
if (hoveringMarker)
|
|
{
|
|
//select the event and activate dragging
|
|
if (leftMousePressed)
|
|
{
|
|
animSceneEditor->SelectEvent(evt);
|
|
}
|
|
if (animSceneEditor->CanDragEvent(evt))
|
|
{
|
|
animSceneEditor->SetFlag(CAnimSceneEditor::kDraggingEvent);
|
|
}
|
|
}
|
|
else if (hoveringPreload)
|
|
{
|
|
//select the event and activate dragging
|
|
if (leftMousePressed)
|
|
{
|
|
animSceneEditor->SelectEvent(evt);
|
|
}
|
|
if (animSceneEditor->CanDragEvent(evt))
|
|
{
|
|
animSceneEditor->SetFlag(CAnimSceneEditor::kDraggingEventPreLoad);
|
|
}
|
|
}
|
|
else if (hoveringEventEnd)
|
|
{
|
|
//select the event and activate dragging
|
|
if (leftMousePressed)
|
|
{
|
|
animSceneEditor->SelectEvent(evt);
|
|
}
|
|
if (animSceneEditor->CanDragEvent(evt))
|
|
{
|
|
animSceneEditor->SetFlag(CAnimSceneEditor::kDraggingEventEnd);
|
|
}
|
|
}
|
|
else if (hoveringEventStart)
|
|
{
|
|
//select the event and activate dragging
|
|
if (leftMousePressed)
|
|
{
|
|
animSceneEditor->SelectEvent(evt);
|
|
}
|
|
if (animSceneEditor->CanDragEvent(evt))
|
|
{
|
|
animSceneEditor->SetFlag(CAnimSceneEditor::kDraggingEventStart);
|
|
}
|
|
}
|
|
else if (hoveringEvent)
|
|
{
|
|
//select the event and activate dragging
|
|
if (leftMousePressed)
|
|
{
|
|
animSceneEditor->SelectEvent(evt);
|
|
}
|
|
if (animSceneEditor->CanDragEvent(evt))
|
|
{
|
|
animSceneEditor->SetFlag(CAnimSceneEditor::kDraggingEvent);
|
|
}
|
|
}
|
|
}
|
|
else // if (leftMouseDown)
|
|
{
|
|
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
bool isSelected = (evt==animSceneEditor->GetSelectedEvent());
|
|
bool hasFocus = isSelected && animSceneEditor->GetFocus()==CAnimSceneEditor::kFocusEvent;
|
|
bool isBeingDragged = isSelected && animSceneEditor->IsDraggingEvent();
|
|
|
|
Vector3 points[4];
|
|
points[0].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[1].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY(), 0.0f);
|
|
points[3].Set(EventScreenExtents.GetMinX(), EventScreenExtents.GetMinY(), 0.0f);
|
|
|
|
eventColor.SetAlpha(255); //No visual alpha blending on events
|
|
|
|
bool drawEventBackground = true;
|
|
if(drawEventBackground)
|
|
{
|
|
Color32 backColor(eventColor);
|
|
backColor = animSceneEditor->GetColor(CAnimSceneEditor::kEventBackgroundColor);
|
|
backColor.SetAlpha((int) (CAnimSceneEditor::ms_editorSettingBackgroundAlpha*255) );
|
|
grcDrawPolygon(points, 4, NULL, true,backColor);
|
|
}
|
|
|
|
if (hoveringEvent && !isSelected)
|
|
{
|
|
eventColor.SetRed(Clamp(eventColor.GetRed() + 25, 0, 255));
|
|
eventColor.SetBlue(Clamp(eventColor.GetBlue() + 25, 0, 255));
|
|
eventColor.SetGreen(Clamp(eventColor.GetGreen() + 25, 0, 255));
|
|
grcDrawPolygon(points, 4, NULL, false,eventColor);
|
|
}
|
|
else
|
|
{
|
|
grcDrawPolygon(points, 4, NULL, false,eventColor);
|
|
}
|
|
|
|
// render the event outline
|
|
grcLighting(false);
|
|
|
|
CAnimSceneEditor::eColorType markerColorType = isSelected ? CAnimSceneEditor::kSelectedEventMarkerColor : CAnimSceneEditor::kEventMarkerColor;
|
|
CAnimSceneEditor::eColorType outlineColorType = isSelected ? isBeingDragged ? CAnimSceneEditor::kSelectedEventDraggingColor : CAnimSceneEditor::kSelectedEventOutlineColor : CAnimSceneEditor::kEventOutlineColor;
|
|
CAnimSceneEditor::eColorType eventColorType = isSelected ? isBeingDragged ? CAnimSceneEditor::kSelectedEventDraggingColor : CAnimSceneEditor::kSelectedEventColor : CAnimSceneEditor::kDefaultEventColor;
|
|
|
|
if(isSelected)
|
|
{
|
|
Color32 outlineColour = animSceneEditor->GetColor(outlineColorType);
|
|
outlineColour.SetAlpha(255);
|
|
grcColor(outlineColour);
|
|
grcBegin(drawLineStrip, 5);
|
|
grcVertex2f(EventScreenExtents.GetMinX(), EventScreenExtents.GetMinY());
|
|
grcVertex2f(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMinY());
|
|
grcVertex2f(EventScreenExtents.GetMaxX(), EventScreenExtents.GetMaxY());
|
|
grcVertex2f(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY());
|
|
grcVertex2f(EventScreenExtents.GetMinX(), EventScreenExtents.GetMinY());
|
|
grcEnd();
|
|
}
|
|
|
|
if (isDurationless && !endXPastLeft && !startFullyInXPastRight)
|
|
{
|
|
// need to draw a marker to support moving durationless tags around
|
|
Vector3 points[4];
|
|
points[0].Set(EventScreenExtents.GetMinX() - s_markerBoxSize, EventScreenExtents.GetMinY() - s_markerBoxSize, 0.0f);
|
|
points[1].Set(EventScreenExtents.GetMinX() + s_markerBoxSize, EventScreenExtents.GetMinY() - s_markerBoxSize, 0.0f);
|
|
points[2].Set(EventScreenExtents.GetMinX() + s_markerBoxSize, EventScreenExtents.GetMinY() + s_markerBoxSize, 0.0f);
|
|
points[3].Set(EventScreenExtents.GetMinX() - s_markerBoxSize, EventScreenExtents.GetMinY() + s_markerBoxSize, 0.0f);
|
|
grcDrawPolygon(points, 4, NULL, true, animSceneEditor->GetColor(markerColorType));
|
|
|
|
Vector3 Outline[4];
|
|
Outline[0].Set(EventScreenExtents.GetMinX() - s_markerBoxSize, EventScreenExtents.GetMinY() - s_markerBoxSize, 0.0f);
|
|
Outline[1].Set(EventScreenExtents.GetMinX() + s_markerBoxSize, EventScreenExtents.GetMinY() - s_markerBoxSize, 0.0f);
|
|
Outline[2].Set(EventScreenExtents.GetMinX() + s_markerBoxSize, EventScreenExtents.GetMinY() + s_markerBoxSize, 0.0f);
|
|
Outline[3].Set(EventScreenExtents.GetMinX() - s_markerBoxSize, EventScreenExtents.GetMinY() + s_markerBoxSize, 0.0f);
|
|
grcDrawPolygon(Outline, 4, NULL, false, animSceneEditor->GetColor(outlineColorType));
|
|
}
|
|
|
|
if (drawStartArrow)
|
|
{
|
|
Vector3 points[3];
|
|
points[0].Set(GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMinY(), 0.0f);
|
|
points[1].Set(GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMaxY(), 0.0f);
|
|
points[2].Set(GroupSceenExtents.GetMinX() - m_offscreenArrowMarker, GroupSceenExtents.GetMinY() + ((GroupSceenExtents.GetMaxY()-GroupSceenExtents.GetMinY())*0.5f), 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, true, animSceneEditor->GetColor(eventColorType));
|
|
|
|
Vector3 arrowOutline[3];
|
|
arrowOutline[0].Set(GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMinY(), 0.0f);
|
|
arrowOutline[1].Set(GroupSceenExtents.GetMinX(), GroupSceenExtents.GetMaxY(), 0.0f);
|
|
arrowOutline[2].Set(GroupSceenExtents.GetMinX() - m_offscreenArrowMarker, GroupSceenExtents.GetMinY() + ((GroupSceenExtents.GetMaxY()-GroupSceenExtents.GetMinY())*0.5f), 0.0f);
|
|
grcDrawPolygon(arrowOutline, 3, NULL, false, animSceneEditor->GetColor(outlineColorType));
|
|
}
|
|
if (drawEndArrow)
|
|
{
|
|
Vector3 points[3];
|
|
points[0].Set(GroupSceenExtents.GetMaxX(), GroupSceenExtents.GetMinY(), 0.0f);
|
|
points[2].Set(GroupSceenExtents.GetMaxX() + m_offscreenArrowMarker, GroupSceenExtents.GetMinY() + ((GroupSceenExtents.GetMaxY()-GroupSceenExtents.GetMinY())*0.5f), 0.0f);
|
|
points[1].Set(GroupSceenExtents.GetMaxX(), EventScreenExtents.GetMaxY(), 0.0f);
|
|
grcDrawPolygon(points, 3, NULL, true, animSceneEditor->GetColor(eventColorType));
|
|
|
|
Vector3 arrowOutline[3];
|
|
arrowOutline[0].Set(GroupSceenExtents.GetMaxX(), GroupSceenExtents.GetMinY(), 0.0f);
|
|
arrowOutline[2].Set(GroupSceenExtents.GetMaxX() + m_offscreenArrowMarker, GroupSceenExtents.GetMinY() + ((GroupSceenExtents.GetMaxY()-GroupSceenExtents.GetMinY())*0.5f), 0.0f);
|
|
arrowOutline[1].Set(GroupSceenExtents.GetMaxX(), GroupSceenExtents.GetMaxY(), 0.0f);
|
|
grcDrawPolygon(arrowOutline, 3, NULL, false, animSceneEditor->GetColor(outlineColorType));
|
|
}
|
|
|
|
if (preloadLength>0.0f && animSceneEditor->GetEditEventPreloads())
|
|
{
|
|
Vector3 points[4];
|
|
points[0].Set(preloadX-s_preloadBoxSize, preloadY-s_preloadBoxSize, 0.0f);
|
|
points[1].Set(preloadX+s_preloadBoxSize, preloadY-s_preloadBoxSize, 0.0f);
|
|
points[2].Set(preloadX+s_preloadBoxSize, preloadY+s_preloadBoxSize, 0.0f);
|
|
points[3].Set(preloadX-s_preloadBoxSize, preloadY+s_preloadBoxSize, 0.0f);
|
|
grcDrawPolygon(points, 4, NULL, true, animSceneEditor->GetColor(markerColorType));
|
|
|
|
grcColor(animSceneEditor->GetColor(CAnimSceneEditor::kEventPreloadLineColor));
|
|
grcBegin(drawLineStrip, 3);
|
|
grcVertex2f(EventScreenExtents.GetMinX(), EventScreenExtents.GetMaxY());
|
|
grcVertex2f(EventScreenExtents.GetMinX(), preloadY);
|
|
grcVertex2f(preloadX, preloadY);
|
|
grcEnd();
|
|
}
|
|
|
|
TUNE_FLOAT(TextPadding, 1.0f, -1.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(TextScale, 1.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(TextYOffset, 1.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_FLOAT(TextXOffset, 1.0f, 0.0f, 100.0f, 1.0f)
|
|
TUNE_BOOL(renderOutline, false)
|
|
|
|
// render the name of the event in the centre of the event bar.
|
|
atString evtText;
|
|
if(evt->GetEditorEventText(evtText, *animSceneEditor))
|
|
{
|
|
Color32 textcolor = isSelected ? animSceneEditor->GetColor(isBeingDragged ? CAnimSceneEditor::kSelectedEventDraggingColor : CAnimSceneEditor::kSelectedEventOutlineColor) : eventColor;
|
|
const float fTextWidth = GetTextWidth(evtText.c_str());
|
|
if(fTextWidth < EventScreenExtents.GetWidth())
|
|
{
|
|
float RenderTextPosx = EventScreenExtents.GetMinX() + EventScreenExtents.GetWidth() / 2.0f - fTextWidth/2.0f;
|
|
|
|
RenderTextWithBackground(evtText.c_str(), RenderTextPosx, EventScreenExtents.GetMinY() + TextYOffset, textcolor,
|
|
animSceneEditor->GetColor(CAnimSceneEditor::kTextBackgroundColor), -1.0f, renderOutline, animSceneEditor->GetColor(hasFocus? CAnimSceneEditor::kFocusTextOutlineColor : isSelected ? CAnimSceneEditor::kSelectedTextOutlineColor : CAnimSceneEditor::kTextOutlineColor));
|
|
}
|
|
}
|
|
|
|
if (hoveringEvent || hoveringMarker)
|
|
{
|
|
atString hoverText;
|
|
if(evt->GetEditorHoverText(hoverText, *animSceneEditor))
|
|
{
|
|
PanelGroup->AddEventInfo(hoverText.c_str());
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
void CEventPanel::DrawDashedLine(const Vector3& v1, const Vector3& v2, const Color32& colour, int numDashes)
|
|
{
|
|
//starting at v1 in the direction of v2 - v1
|
|
Vector3 dirInc = (v2 - v1) / (2.0f * numDashes);
|
|
Vector3 line;
|
|
for(int i = 0; i < numDashes; ++i)
|
|
{
|
|
line = v1 + (dirInc* (float)i *2.0f);
|
|
grcDrawLine(line,line+dirInc, colour);
|
|
}
|
|
}
|
|
|
|
void CEventPanel::DrawTransitionBlock(const Vector3 *points, const Color32& leftColour, const Color32& rightColour)
|
|
{
|
|
//void grcDrawPolygon(const Vector3 *points, int count, const Vector3 *pNormal, bool solid, Color32 *color)
|
|
Color32 colourList[4];
|
|
colourList[0] = Color32(leftColour);
|
|
colourList[1] = Color32(leftColour);
|
|
colourList[2] = Color32(rightColour);
|
|
colourList[3] = Color32(rightColour);
|
|
grcDrawPolygon(points,4,NULL,true,colourList);
|
|
}
|
|
|
|
|
|
|
|
CEventPanelGroup::CEventPanelGroup(atHashString name)
|
|
:m_name(name)
|
|
,m_GroupHeight(10.0f)
|
|
,m_GroupSpacing(3.0f)
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
CEventPanelGroup::~CEventPanelGroup()
|
|
{
|
|
RemoveAllEvents();
|
|
}
|
|
|
|
void CEventPanelGroup::AddEvent(EventInfo Info)
|
|
{
|
|
for(int i=0; i < m_events.GetCount(); i++)
|
|
{
|
|
if(m_events[i])
|
|
{
|
|
if(Info.event == m_events[i]->GetEventInfo().event)
|
|
{
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
|
|
m_events.Grow() = rage_new CEventPanel(Info);
|
|
}
|
|
|
|
void CEventPanelGroup::RemoveAllEvents()
|
|
{
|
|
for(int i=0; i < m_events.GetCount(); i++)
|
|
{
|
|
if(m_events[i])
|
|
{
|
|
delete m_events[i];
|
|
m_events[i] = NULL;
|
|
}
|
|
}
|
|
|
|
m_events.Reset();
|
|
}
|
|
|
|
|
|
void CEventPanelGroup::RemoveEvent(EventInfo Info)
|
|
{
|
|
for(int i=0; i < m_events.GetCount(); i++)
|
|
{
|
|
if(m_events[i])
|
|
{
|
|
if(Info.event == m_events[i]->GetEventInfo().event)
|
|
{
|
|
delete m_events[i];
|
|
m_events[i] = NULL;
|
|
|
|
m_events.Delete(i);
|
|
}
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
void CEventPanelGroup::SetScreenExtents(const CScreenExtents& screenExtents)
|
|
{
|
|
m_screenExtents = screenExtents;
|
|
}
|
|
|
|
int CEventPanelGroup::CompareEvents( CEventPanel* const* pEvent1, CEventPanel* const* pEvent2)
|
|
{
|
|
Assert(pEvent1);
|
|
Assert(pEvent2);
|
|
|
|
if (pEvent1 && pEvent2)
|
|
{
|
|
if((*pEvent1)->GetEventInfo().event->GetStart() < (*pEvent2)->GetEventInfo().event->GetStart())
|
|
{
|
|
return -1;
|
|
}
|
|
else
|
|
{
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
|
|
|
|
void CEventPanelGroup::Render(CAnimSceneEditor* animSceneEditor)
|
|
{
|
|
TUNE_FLOAT(GroupHeightOffset, 3.0f, 0.0f, 1000.0f, 1.0f)
|
|
TUNE_FLOAT(GroupSpacing, 6.0f, 0.0f, 1000.0f, 1.0f)
|
|
TUNE_FLOAT(GapMarkerOffset, 34.0f, 0.0f, 100.0f, 0.5f)
|
|
|
|
m_HoveringInfo.Reset();
|
|
|
|
m_GroupHeight = GetTextHeight() + GroupHeightOffset;
|
|
m_GroupSpacing = GroupSpacing;
|
|
|
|
m_events.QSort(0, -1, &CompareEvents);
|
|
|
|
//render the track's extents
|
|
/*
|
|
grcColor(animSceneEditor->GetColor(CAnimSceneEditor::kEventCurrentTimeLineColor));
|
|
grcBegin(drawLineStrip, 5);
|
|
grcVertex2f(m_screenExtents.GetMinX() , m_screenExtents.GetMinY() );
|
|
grcVertex2f(m_screenExtents.GetMaxX() , m_screenExtents.GetMinY() );
|
|
|
|
grcVertex2f(m_screenExtents.GetMaxX() , m_screenExtents.GetMaxY() );
|
|
grcVertex2f(m_screenExtents.GetMinX() , m_screenExtents.GetMaxY() );
|
|
|
|
grcVertex2f(m_screenExtents.GetMinX() , m_screenExtents.GetMinY() );
|
|
grcEnd();*/
|
|
|
|
//Render section starts as black lines behind events
|
|
if(animSceneEditor->GetScene())
|
|
{
|
|
|
|
//Draw double section time marker at beginning of anim scene timeline
|
|
float animSceneStartX = animSceneEditor->GetTimeLine().GetScreenX(0.f);
|
|
if( animSceneStartX <= m_screenExtents.GetMaxX() && animSceneStartX >= m_screenExtents.GetMinX() )
|
|
{
|
|
grcColor(animSceneEditor->GetColor(CAnimSceneEditor::kSectionDividerColor));
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(animSceneStartX,
|
|
m_screenExtents.GetMinY() - GetGroupSpacing() );
|
|
grcVertex2f(animSceneStartX,
|
|
m_screenExtents.GetMaxY() + GetGroupSpacing() );
|
|
grcEnd();
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(animSceneStartX -2.f,
|
|
m_screenExtents.GetMinY() - GetGroupSpacing() );
|
|
grcVertex2f(animSceneStartX -2.f,
|
|
m_screenExtents.GetMaxY() + GetGroupSpacing() );
|
|
grcEnd();
|
|
}
|
|
|
|
CAnimScenePlaybackList::Id currentPBL = animSceneEditor->GetScene()->GetPlayBackList();
|
|
if(currentPBL == ANIM_SCENE_SECTION_DEFAULT || currentPBL == ANIM_SCENE_SECTION_ID_INVALID)
|
|
{
|
|
//render for all sections if we are the default play back list
|
|
CAnimSceneSectionIterator sectionIt(*animSceneEditor->GetScene(), true);
|
|
while (*sectionIt)
|
|
{
|
|
CAnimSceneSection::Id secId = sectionIt.GetId();
|
|
CAnimSceneSection* section = animSceneEditor->GetScene()->GetSection(secId);
|
|
animAssertf(section,"Section was invalid for id %s",secId.TryGetCStr());
|
|
float secStartTime = animSceneEditor->GetScene()->CalcSectionStartTime(section,currentPBL);
|
|
float secStartTimeXLoc = animSceneEditor->GetTimeLine().GetScreenX(secStartTime);
|
|
|
|
if( secStartTimeXLoc <= m_screenExtents.GetMaxX() && secStartTimeXLoc >= m_screenExtents.GetMinX() )
|
|
{
|
|
grcColor(animSceneEditor->GetColor(CAnimSceneEditor::kSectionDividerColor));
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(secStartTimeXLoc, m_screenExtents.GetMinY() - GetGroupSpacing() );
|
|
grcVertex2f(secStartTimeXLoc, m_screenExtents.GetMaxY() + GetGroupSpacing() );
|
|
grcEnd();
|
|
}
|
|
++sectionIt;
|
|
}
|
|
}
|
|
else if(animSceneEditor->GetScene()->GetPlayBackList(currentPBL))
|
|
{
|
|
for(int i = 0; i < animSceneEditor->GetScene()->GetPlayBackList(currentPBL)->GetNumSections(); ++i)
|
|
{
|
|
CAnimSceneSection::Id secId = animSceneEditor->GetScene()->GetPlayBackList(currentPBL)->GetSectionId(i);
|
|
CAnimSceneSection* section = animSceneEditor->GetScene()->GetSection(secId);
|
|
animAssertf(section,"Section was invalid for id %s",secId.TryGetCStr());
|
|
float secStartTime = animSceneEditor->GetScene()->CalcSectionStartTime(section,currentPBL);
|
|
float secStartTimeXLoc = animSceneEditor->GetTimeLine().GetScreenX(secStartTime);
|
|
|
|
if( secStartTimeXLoc <= m_screenExtents.GetMaxX() && secStartTimeXLoc >= m_screenExtents.GetMinX() )
|
|
{
|
|
grcColor(animSceneEditor->GetColor(CAnimSceneEditor::kSectionDividerColor));
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(secStartTimeXLoc, m_screenExtents.GetMinY() - GetGroupSpacing() );
|
|
grcVertex2f(secStartTimeXLoc, m_screenExtents.GetMaxY() + GetGroupSpacing() );
|
|
grcEnd();
|
|
}
|
|
}
|
|
}
|
|
|
|
//Draw double section time marker at end of anim scene timeline
|
|
float animSceneEndX = animSceneEditor->GetTimeLine().GetScreenX(animSceneEditor->GetScene()->GetDuration());
|
|
if( animSceneEndX <= m_screenExtents.GetMaxX() && animSceneEndX >= m_screenExtents.GetMinX() )
|
|
{
|
|
grcColor(animSceneEditor->GetColor(CAnimSceneEditor::kSectionDividerColor));
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(animSceneEndX,
|
|
m_screenExtents.GetMinY() - GetGroupSpacing() );
|
|
grcVertex2f(animSceneEndX,
|
|
m_screenExtents.GetMaxY() + GetGroupSpacing() );
|
|
grcEnd();
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(animSceneEndX +2.f,
|
|
m_screenExtents.GetMinY() - GetGroupSpacing() );
|
|
grcVertex2f(animSceneEndX +2.f,
|
|
m_screenExtents.GetMaxY() + GetGroupSpacing() );
|
|
grcEnd();
|
|
}
|
|
}
|
|
|
|
//Render the actual event boxes
|
|
for(int i=0; i < m_events.GetCount(); i++)
|
|
{
|
|
m_events[i]->Render(animSceneEditor, m_screenExtents, this, i);
|
|
}
|
|
|
|
//Might be a good idea to have a seperate 'render event controls' to separate rendering the events and the overlayed blending markers
|
|
//This renders both
|
|
for(int i=0; i < m_events.GetCount(); i++)
|
|
{
|
|
m_events[i]->RenderToolsOverlay(animSceneEditor, m_screenExtents, this, i);
|
|
}
|
|
|
|
// Render current time marker
|
|
float currentTimeX = animSceneEditor->GetTimeLine().GetScreenX(animSceneEditor->GetScene()->GetTime());
|
|
if (currentTimeX >= m_screenExtents.GetMinX() && currentTimeX <= m_screenExtents.GetMaxX())
|
|
{
|
|
// White line at time
|
|
grcColor(animSceneEditor->GetColor(CAnimSceneEditor::kEventCurrentTimeLineColor));
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(currentTimeX, m_screenExtents.GetMinY() - GetGroupSpacing() );
|
|
grcVertex2f(currentTimeX, m_screenExtents.GetMaxY() + GetGroupSpacing() );
|
|
grcEnd();
|
|
}
|
|
|
|
RenderEventInfoOverlay(animSceneEditor);
|
|
|
|
//Check the first event to see if it's a play anim event, and if so, check and notify if there are gaps
|
|
if(m_events.size() > 0
|
|
&& m_events[0]
|
|
&& m_events[0]->GetEventInfo().event
|
|
&& m_events[0]->GetEventInfo().event->GetType() == AnimSceneEventType::PlayAnimEvent
|
|
&& DoesGroupHaveGaps())
|
|
{
|
|
RenderTextWithBackground("(!)", m_screenExtents.GetMinX() - GapMarkerOffset, m_screenExtents.GetMinY(), animSceneEditor->GetColor(CAnimSceneEditor::kTextWarningColor),
|
|
animSceneEditor->GetColor(CAnimSceneEditor::kTextBackgroundColor), 1.1f, true, animSceneEditor->GetColor(CAnimSceneEditor::kTextOutlineColor));
|
|
}
|
|
}
|
|
|
|
void CEventPanelGroup::AddEventInfo(const char* EventInfo)
|
|
{
|
|
atString& mString = m_HoveringInfo.Grow();
|
|
|
|
mString += EventInfo;
|
|
}
|
|
|
|
void CEventPanelGroup::RenderEventInfoOverlay(CAnimSceneEditor* animSceneEditor)
|
|
{
|
|
float mouseX = static_cast<float>(ioMouse::GetX());
|
|
float mouseY = static_cast<float>(ioMouse::GetY());
|
|
TUNE_FLOAT(mouseyOffset, -22.0f, -100.0f, 10000.0f, 1.0f)
|
|
TUNE_FLOAT(mouseXOffset, 0.0f, 0.0f, 10000.0f, 1.0f)
|
|
TUNE_FLOAT(textSize, 10.0f, 0.0f, 10000.0f, 1.0f)
|
|
for(int i = 0; i < m_HoveringInfo.GetCount() ; i++)
|
|
{
|
|
RenderTextWithBackground(m_HoveringInfo[i], (mouseX + mouseXOffset), mouseY + mouseyOffset + (i * textSize) , animSceneEditor->GetColor(CAnimSceneEditor::kMainTextColor),
|
|
animSceneEditor->GetColor(CAnimSceneEditor::kTextBackgroundColor), 1.0f, true, animSceneEditor->GetColor(CAnimSceneEditor::kTextOutlineColor));
|
|
}
|
|
|
|
}
|
|
|
|
//This function does not assume m_events is sorted
|
|
bool CEventPanelGroup::DoesGroupHaveGaps()
|
|
{
|
|
//list of X locations or times
|
|
atArray<float> locStarts;
|
|
atArray<float> locEnds;
|
|
|
|
//the blend in and out times
|
|
atArray<float> blendStarts;
|
|
atArray<float> blendEnds;
|
|
|
|
locStarts.Reserve(m_events.size());
|
|
locEnds.Reserve(m_events.size());
|
|
blendStarts.Reserve(m_events.size());
|
|
blendEnds.Reserve(m_events.size());
|
|
|
|
for(int i = 0; i < m_events.size(); ++i)
|
|
{
|
|
CAnimSceneEvent* event = m_events[i]->GetEventInfo().event;
|
|
if(event->GetType() == AnimSceneEventType::PlayAnimEvent)
|
|
{
|
|
CAnimScenePlayAnimEvent* evtPA = static_cast<CAnimScenePlayAnimEvent*>(event);
|
|
locStarts.PushAndGrow(evtPA->GetStartFullBlendInTime());
|
|
blendStarts.PushAndGrow(evtPA->GetStart());
|
|
locEnds.PushAndGrow(evtPA->GetEnd());
|
|
blendEnds.PushAndGrow(evtPA->GetEnd() + evtPA->GetPoseBlendOutDuration());
|
|
}
|
|
else
|
|
{
|
|
locStarts.PushAndGrow(event->GetStart());
|
|
blendStarts.PushAndGrow(event->GetStart());
|
|
locEnds.PushAndGrow(event->GetEnd());
|
|
blendEnds.PushAndGrow(event->GetEnd());
|
|
}
|
|
|
|
}
|
|
|
|
int numMismatchedStarts = 0;
|
|
for(int i = 0; i < locStarts.size(); ++i)
|
|
{
|
|
//find an end for each start (end must be after start, and beginning must be before)
|
|
float toFind = locStarts[i];
|
|
//Custom float find with epsilon
|
|
float eps = 1e-3f;
|
|
bool found = false;
|
|
for(int j = 0; j < locEnds.size(); ++j)
|
|
{
|
|
if(i == j) continue;
|
|
//toFind is in between start and end of other clip (or on it)
|
|
if(toFind > locStarts[j] - eps && toFind < locEnds[j] + eps)
|
|
{
|
|
found = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if(!found)
|
|
{
|
|
//Check whether there is a blend prior to this, and if that starts at
|
|
//the end of a previous clip
|
|
int findId = -1;
|
|
float bStart = blendStarts[i];
|
|
for(int j = 0; j < locEnds.size(); ++j)
|
|
{
|
|
if(i == j) continue;
|
|
|
|
//The blend occurs during the main section of event j
|
|
if(bStart > locStarts[j] - eps && bStart < locEnds[j] + eps)
|
|
{
|
|
findId = j;
|
|
//For extra care, check the end of the previous clip blend finishes at
|
|
//the start of this event being fully blended in (or later)
|
|
if(blendEnds[findId] > locStarts[i] - eps)
|
|
{
|
|
found = true;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
if(!found)
|
|
{
|
|
++numMismatchedStarts;
|
|
//should have one initial start which does not match to an end.
|
|
if(numMismatchedStarts > 1)
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
//There were 1 or 0 mismatched starts
|
|
return false;
|
|
}
|
|
|
|
|
|
|
|
|
|
CEventLayerPanel::CEventLayerPanel(atHashString name)
|
|
:m_name(name)
|
|
,m_basePanelInfoHeight(15.0f)
|
|
,m_basePanelSpacing(15.0f)
|
|
{
|
|
|
|
}
|
|
|
|
CEventLayerPanel::~CEventLayerPanel()
|
|
{
|
|
for(int i = 0; i < m_groups.GetCount(); i++)
|
|
{
|
|
delete m_groups[i];
|
|
m_groups[i] = NULL;
|
|
}
|
|
|
|
m_groups.Reset();
|
|
}
|
|
|
|
void CEventLayerPanel::AddEventGroup(atHashString name)
|
|
{
|
|
m_groups.Grow() = rage_new CEventPanelGroup(name);
|
|
}
|
|
|
|
void CEventLayerPanel::RemoveEventGroup(u32 i)
|
|
{
|
|
if(i < m_groups.GetCount())
|
|
{
|
|
delete m_groups[i];
|
|
m_groups[i] = NULL;
|
|
m_groups.Delete(i);
|
|
}
|
|
}
|
|
|
|
void CEventLayerPanel::RenderPanelInfo(CAnimSceneEditor* animSceneEditor)
|
|
{
|
|
if(animSceneEditor)
|
|
{
|
|
float mouseX = static_cast<float>(ioMouse::GetX());
|
|
float mouseY = static_cast<float>(ioMouse::GetY());
|
|
|
|
bool isSelected = (GetName().GetHash()==animSceneEditor->GetSelectedEntityId().GetHash());
|
|
bool hasFocus = isSelected && animSceneEditor->GetFocus()==CAnimSceneEditor::kFocusEntity;
|
|
bool isHovering = false;
|
|
|
|
if(m_name.GetHash() != 0)
|
|
{
|
|
const float fTextWidth = GetTextWidth(m_name.GetCStr());
|
|
|
|
CScreenExtents EventLayerPanelIdScreenExtents(m_screenExtents.GetMinX(), m_screenExtents.GetMinY(), m_screenExtents.GetMinX()+fTextWidth, m_screenExtents.GetMinY()+ m_basePanelInfoHeight);
|
|
|
|
if (EventLayerPanelIdScreenExtents.Contains(mouseX,mouseY))
|
|
{
|
|
if (ioMouse::GetButtons() & ioMouse::MOUSE_LEFT && !animSceneEditor->IsDragging())
|
|
{
|
|
if(animSceneEditor->GetScene())
|
|
{
|
|
animSceneEditor->SelectEntity(animSceneEditor->GetScene()->GetEntity(GetName().GetCStr()));
|
|
}
|
|
animSceneEditor->SetFlag(CAnimSceneEditor::kMadeEntitySelectionThisFrame);
|
|
}
|
|
else
|
|
{
|
|
isHovering = true;
|
|
}
|
|
}
|
|
|
|
if(m_screenExtents.Contains(mouseX, mouseY))
|
|
{
|
|
RenderTextWithBackground(GetName().GetCStr(), m_screenExtents.GetMinX(), m_screenExtents.GetMinY(),
|
|
animSceneEditor->GetColor(isHovering ? CAnimSceneEditor::kSelectedTextHoverColor : CAnimSceneEditor::kSelectedTextColor),
|
|
animSceneEditor->GetColor(isSelected ? CAnimSceneEditor::kSelectedTextBackGroundColor :CAnimSceneEditor::kTextBackgroundColor), 3.0f, true,
|
|
animSceneEditor->GetColor(hasFocus ? CAnimSceneEditor::kFocusTextOutlineColor : isSelected ? CAnimSceneEditor::kSelectedTextOutlineColor :CAnimSceneEditor::kTextOutlineColor));
|
|
}
|
|
else
|
|
{
|
|
RenderTextWithBackground(GetName().GetCStr(), m_screenExtents.GetMinX(), m_screenExtents.GetMinY(),
|
|
animSceneEditor->GetColor(isHovering ? CAnimSceneEditor::kTextHoverColor : CAnimSceneEditor::kMainTextColor),
|
|
animSceneEditor->GetColor(isSelected ? CAnimSceneEditor::kSelectedTextBackGroundColor :CAnimSceneEditor::kTextBackgroundColor), 3.0f, true,
|
|
animSceneEditor->GetColor(hasFocus ? CAnimSceneEditor::kFocusTextOutlineColor : isSelected ? CAnimSceneEditor::kSelectedTextOutlineColor : CAnimSceneEditor::kTextOutlineColor));
|
|
}
|
|
|
|
if (isSelected)
|
|
{
|
|
// draw a colored box to mark the selection
|
|
CScreenExtents outline(m_screenExtents.GetMinX() - 6.0f, m_screenExtents.GetMinY() - 6.0f, animSceneEditor->GetTimeLine().GetScreenExtents().GetMaxX() - 6.0f, m_screenExtents.GetMaxY() - 6.0f);
|
|
outline.DrawBorder(animSceneEditor->GetColor(hasFocus ? CAnimSceneEditor::kFocusTextOutlineColor : CAnimSceneEditor::kSelectedTextOutlineColor));
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
void CEventLayerPanel::Render(CAnimSceneEditor* animSceneEditor)
|
|
{
|
|
TUNE_FLOAT(basePanelSpacing, 6.000f, 0.0f, 100.0f, 1.0f)
|
|
|
|
m_basePanelInfoHeight= GetTextHeight();
|
|
m_basePanelSpacing = basePanelSpacing;
|
|
|
|
RenderPanelInfo(animSceneEditor);
|
|
|
|
CScreenExtents m_EventGroupExtents;
|
|
for(int i= 0; i < m_groups.GetCount(); i++)
|
|
{
|
|
if(m_groups[i])
|
|
{
|
|
float EventGroupHeightMin = (i * (float)m_groups[i]->GetGroupHeight()) + (i>0 ? (float)m_groups[i]->GetGroupSpacing() : 0.0f);
|
|
float EventGroupHeightMax = EventGroupHeightMin + (float)(m_groups[i]->GetGroupHeight());
|
|
|
|
m_EventGroupExtents.Set(animSceneEditor->GetTimeLine().GetScreenExtents().GetMinX(), m_screenExtents.GetMinY() + EventGroupHeightMin,
|
|
animSceneEditor->GetTimeLine().GetScreenExtents().GetMaxX(), m_screenExtents.GetMinY() + EventGroupHeightMax);
|
|
|
|
m_groups[i]->SetScreenExtents(CScreenExtents(m_EventGroupExtents));
|
|
m_groups[i]->Render(animSceneEditor);
|
|
}
|
|
}
|
|
}
|
|
|
|
float CEventLayerPanel::GetTotalPanelHeight()
|
|
{
|
|
float panelHeight = 0.0f;
|
|
for(int i =0; i < m_groups.GetCount(); i++)
|
|
{
|
|
panelHeight += m_groups[i]->GetGroupPanelHeight();
|
|
}
|
|
|
|
panelHeight+=m_basePanelSpacing;
|
|
|
|
if(panelHeight> m_basePanelInfoHeight + m_basePanelSpacing)
|
|
{
|
|
return panelHeight;
|
|
}
|
|
else
|
|
{
|
|
return m_basePanelInfoHeight + m_basePanelSpacing;
|
|
}
|
|
|
|
}
|
|
|
|
void CEventLayerPanel::SetScreenExtents(const CScreenExtents& screenExtents)
|
|
{
|
|
m_screenExtents = screenExtents;
|
|
}
|
|
|
|
CEventLayersPane::CEventLayersPane()
|
|
{
|
|
m_eventLayerPanels.Reset();
|
|
}
|
|
|
|
CEventLayersPane::~CEventLayersPane()
|
|
{
|
|
for(int i = 0; i < m_eventLayerPanels.GetCount(); i++)
|
|
{
|
|
delete m_eventLayerPanels[i];
|
|
m_eventLayerPanels[i] = NULL;
|
|
}
|
|
|
|
m_eventLayerPanels.Reset();
|
|
}
|
|
|
|
|
|
void CEventLayersPane::AddEventLayerPanel(atHashString Name)
|
|
{
|
|
m_eventLayerPanels.Grow() = rage_new CEventLayerPanel(Name);
|
|
}
|
|
|
|
void CEventLayersPane::SetScreenExtents(const CScreenExtents& screenExtents)
|
|
{
|
|
m_screenExtents = screenExtents;
|
|
}
|
|
|
|
CEventPanelGroup* CEventLayersPane::GetEventPanelGroup(u32 PanelLayer, u32 Group)
|
|
{
|
|
CEventPanelGroup* pGroupPanel = NULL;
|
|
|
|
if(PanelLayer < (u32)m_eventLayerPanels.GetCount())
|
|
{
|
|
if(m_eventLayerPanels[PanelLayer] && Group < m_eventLayerPanels[PanelLayer]->GetEventGroup().GetCount())
|
|
{
|
|
pGroupPanel = m_eventLayerPanels[PanelLayer]->GetEventGroup()[Group];
|
|
}
|
|
}
|
|
|
|
return pGroupPanel;
|
|
}
|
|
|
|
void CEventLayersPane::Render(CAnimSceneEditor* animSceneEditor)
|
|
{
|
|
Vector2 EventPanelMin(m_screenExtents.GetMinX(), m_screenExtents.GetMinY());
|
|
|
|
EventPanelMin.y += animSceneEditor->GetEventLayersYScreenOffset();
|
|
|
|
Vector2 EventPanelMax(m_screenExtents.GetMaxX(), m_screenExtents.GetMaxY());
|
|
|
|
//render the whole event pane
|
|
//Render container surround groups and the timeline
|
|
/*
|
|
float eventsHeightMin = m_screenExtents.GetMinY();
|
|
//float eventsHeightMax = m_screenExtents.GetMinY() + eventsHeightMin + ( m_groups.GetCount() > 0 ? (float)(m_groups[0]->GetGroupHeight()) : 0 );
|
|
float padding = 15.0f;
|
|
float underneathTimeline = (float)SCREEN_HEIGHT - 10.0f;
|
|
|
|
grcColor(animSceneEditor->GetColor(CAnimSceneEditor::kSelectedTextColor));
|
|
grcBegin(drawLineStrip,5);
|
|
grcVertex2f(m_screenExtents.GetMinX() - padding, eventsHeightMin);
|
|
grcVertex2f(m_screenExtents.GetMaxX() + padding, eventsHeightMin);
|
|
grcVertex2f(m_screenExtents.GetMaxX() + padding, underneathTimeline);
|
|
grcVertex2f(m_screenExtents.GetMinX() - padding, underneathTimeline);
|
|
|
|
grcVertex2f(m_screenExtents.GetMinX() - padding, eventsHeightMin);
|
|
grcEnd();*/
|
|
|
|
for(int i = 0; i < m_eventLayerPanels.GetCount(); i++)
|
|
{
|
|
float PanelHeight = m_eventLayerPanels[i]->GetTotalPanelHeight();
|
|
|
|
EventPanelMax.y = EventPanelMin.y + PanelHeight;
|
|
|
|
if(! (EventPanelMin.y < m_screenExtents.GetMinY() || EventPanelMax.y > m_screenExtents.GetMaxY()) )
|
|
{
|
|
m_eventLayerPanels[i]->SetScreenExtents(CScreenExtents(EventPanelMin, EventPanelMax));
|
|
m_eventLayerPanels[i]->Render(animSceneEditor);
|
|
}
|
|
|
|
EventPanelMin.y = EventPanelMax.y;
|
|
}
|
|
}
|
|
|
|
void CEventLayersPane::RemoveEventLayerPanel(int i)
|
|
{
|
|
if(m_eventLayerPanels[i])
|
|
{
|
|
delete m_eventLayerPanels[i];
|
|
m_eventLayerPanels[i] = NULL;
|
|
|
|
m_eventLayerPanels.Delete(i);
|
|
}
|
|
}
|
|
|
|
atHashString CSectioningPanel::ms_NoListString("*");
|
|
atHashString CSectioningPanel::ms_InvalidPlaybackListId(ANIM_SCENE_PLAYBACK_LIST_ID_INVALID);
|
|
atHashString CSectioningPanel::ms_InvalidSectionId(ANIM_SCENE_SECTION_ID_INVALID);
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
void CSectioningPanel::Render(CAnimSceneEditor* animSceneEditor)
|
|
{
|
|
Vector2 EventPanelMin(m_screenExtents.GetMinX(), m_screenExtents.GetMinY());
|
|
Vector2 EventPanelMax(m_screenExtents.GetMaxX(), m_screenExtents.GetMaxY());
|
|
float mouseX = static_cast<float>(ioMouse::GetX());
|
|
float mouseY = static_cast<float>(ioMouse::GetY());
|
|
bool leftMouseDown = ioMouse::GetButtons() & ioMouse::MOUSE_LEFT;
|
|
|
|
bool playbackListHasFocus = false;
|
|
|
|
CAnimScene* pScene = animSceneEditor->GetScene();
|
|
|
|
if (pScene)
|
|
{
|
|
float xOffset = m_scrollOffset;
|
|
const float spacing = 15.0f;
|
|
s32 hoveredSectionIndex = -1;
|
|
Vector2 selectedListBL(0.0f, 0.0f), selectedListBR(0.0f, 0.0f);
|
|
|
|
//Render complete extents
|
|
Color32 outlineColour = animSceneEditor->GetColor(CAnimSceneEditor::kRegionOutlineColor);
|
|
outlineColour.SetAlpha(255);
|
|
grcColor(outlineColour);
|
|
|
|
grcBegin(drawLineStrip,5);
|
|
grcVertex2f(m_screenExtents.GetMinX() - spacing + xOffset,m_screenExtents.GetMinY() - spacing);
|
|
grcVertex2f(m_screenExtents.GetMinX() - spacing + xOffset,m_screenExtents.GetMaxY() + spacing);
|
|
|
|
grcVertex2f((float)SCREEN_WIDTH,m_screenExtents.GetMaxY() + spacing);
|
|
grcVertex2f((float)SCREEN_WIDTH,m_screenExtents.GetMinY() - spacing);
|
|
|
|
grcVertex2f(m_screenExtents.GetMinX() - spacing + xOffset,m_screenExtents.GetMinY() - spacing);
|
|
grcEnd();
|
|
|
|
//Render a draggable bar to adjust x offset of playback list and sections
|
|
//Initially go through and work out the total size of the playback lists and sections
|
|
float playbackListTotalXSize = 0.f;
|
|
float sectionListTotalXSize = 0.f;
|
|
for (s32 i=-1; i<pScene->GetPlayBackLists().GetCount(); i++)
|
|
{
|
|
CAnimScenePlaybackList::Id listId;
|
|
|
|
if (i==-1)
|
|
{
|
|
listId = ms_NoListString;
|
|
}
|
|
else
|
|
{
|
|
listId = *pScene->GetPlayBackLists().GetKey(i);
|
|
}
|
|
|
|
float width = GetTextWidth(listId.GetCStr()) + spacing;
|
|
playbackListTotalXSize += width;
|
|
}
|
|
CAnimSceneSectionIterator sectionIt(*pScene, true);
|
|
while (*sectionIt)
|
|
{
|
|
CAnimSceneSection::Id id = sectionIt.GetId();
|
|
float width = GetTextWidth(id.GetCStr()) + spacing;
|
|
sectionListTotalXSize += width;
|
|
++sectionIt;
|
|
}
|
|
|
|
//Check whether the playback list or section list goes off the side of the screen
|
|
if(m_screenExtents.GetMinX() + playbackListTotalXSize > m_screenExtents.GetMaxX() ||
|
|
m_screenExtents.GetMinX() + sectionListTotalXSize > m_screenExtents.GetMaxX() )
|
|
{
|
|
//percentage of playback list on screen
|
|
float totalScreenX = m_screenExtents.GetMaxX() - m_screenExtents.GetMinX();
|
|
float playbackListOnScreenAmount = totalScreenX/playbackListTotalXSize;
|
|
|
|
float sectionsOnScreenAmount = totalScreenX/sectionListTotalXSize;
|
|
|
|
//We use the playback list size if there's less on screen (it is larger)
|
|
bool usingPlaybackListSize = playbackListOnScreenAmount < sectionsOnScreenAmount;
|
|
|
|
m_scrollbar.SetBackgroundColour(animSceneEditor->GetColor(CAnimSceneEditor::kScrollBarBackgroundColour));
|
|
m_scrollbar.SetForegroundColour(animSceneEditor->GetColor(CAnimSceneEditor::kMainTextColor));
|
|
m_scrollbar.SetTopLeft(Vector2(m_screenExtents.GetMinX(),m_screenExtents.GetMaxY()));
|
|
m_scrollbar.SetMinValue(0.f);
|
|
|
|
if(usingPlaybackListSize)
|
|
{
|
|
m_scrollbar.SetMaxValue(playbackListTotalXSize);
|
|
m_scrollbar.SetBarSize(playbackListOnScreenAmount);
|
|
if(playbackListOnScreenAmount >= 1.f)
|
|
{
|
|
m_scrollbar.SetBarHidden(true);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
m_scrollbar.SetMaxValue(sectionListTotalXSize);
|
|
m_scrollbar.SetBarSize(sectionsOnScreenAmount);
|
|
if(sectionsOnScreenAmount >= 1.f)
|
|
{
|
|
m_scrollbar.SetBarHidden(true);
|
|
}
|
|
}
|
|
|
|
m_scrollbar.SetLength(m_screenExtents.GetMaxX() - m_screenExtents.GetMinX());
|
|
m_scrollbar.SetValue(m_scrollOffset*-1.f);
|
|
if(m_scrollbar.IsDragging() || !animSceneEditor->IsDragging())
|
|
{
|
|
m_scrollbar.ProcessMouseInput();
|
|
}
|
|
m_scrollbar.Render();
|
|
m_scrollOffset = m_scrollbar.GetValue() * -1.f;
|
|
if(m_scrollbar.IsDragging())
|
|
{
|
|
m_flags.SetFlag(kDraggingScrollBar);
|
|
}
|
|
else
|
|
{
|
|
m_flags.ClearFlag(kDraggingScrollBar);
|
|
}
|
|
}
|
|
else //All sections and PBLs are on screen, ensure the screen is positioned at the default location
|
|
{
|
|
m_scrollOffset = 0.f;
|
|
}
|
|
|
|
// render the available playback lists in a row.
|
|
for (s32 i=-1; i<pScene->GetPlayBackLists().GetCount(); i++)
|
|
{
|
|
CAnimScenePlaybackList::Id listId;
|
|
|
|
if (i==-1)
|
|
{
|
|
listId = ms_NoListString;
|
|
}
|
|
else
|
|
{
|
|
listId = *pScene->GetPlayBackLists().GetKey(i);
|
|
}
|
|
|
|
float width = GetTextWidth(listId.GetCStr()) + spacing;
|
|
bool isHovering = (mouseX>=m_screenExtents.GetMinX() + xOffset) && (mouseX<=m_screenExtents.GetMinX() + xOffset + GetTextWidth(listId.GetCStr()))
|
|
&& (mouseY>=m_screenExtents.GetMinY()) && (mouseY<=m_screenExtents.GetMinY()+GetTextHeight());
|
|
bool isSelected = listId.GetHash()==m_selectedList.GetHash();
|
|
bool hasFocus = isSelected && animSceneEditor->GetFocus()==CAnimSceneEditor::kFocusPlaybackList;
|
|
playbackListHasFocus |= hasFocus;
|
|
|
|
RenderTextWithBackground(listId.GetCStr(), m_screenExtents.GetMinX() + xOffset, m_screenExtents.GetMinY(),
|
|
animSceneEditor->GetColor(isHovering ? CAnimSceneEditor::kSelectedTextHoverColor : isSelected ? CAnimSceneEditor::kSelectedTextColor : CAnimSceneEditor::kMainTextColor),
|
|
animSceneEditor->GetColor(isSelected ? CAnimSceneEditor::kSelectedTextBackGroundColor :CAnimSceneEditor::kTextBackgroundColor), 3.0f, true,
|
|
animSceneEditor->GetColor(hasFocus ? CAnimSceneEditor::kFocusTextOutlineColor : isSelected ? CAnimSceneEditor::kSelectedTextOutlineColor :CAnimSceneEditor::kTextOutlineColor));
|
|
|
|
if (isHovering && !animSceneEditor->IsDragging() && leftMouseDown)
|
|
{
|
|
m_selectedList = listId;
|
|
m_flags.SetFlag(kSelectedListChanged);
|
|
animSceneEditor->SetFocus(CAnimSceneEditor::kFocusPlaybackList);
|
|
if (m_selectedList!=ms_InvalidPlaybackListId)
|
|
{
|
|
// always reset the selected section if not displaying the master list
|
|
m_selectedSection = ANIM_SCENE_SECTION_ID_INVALID;
|
|
}
|
|
}
|
|
|
|
// render a selection box around the selected list
|
|
if (m_selectedList==listId)
|
|
{
|
|
float xMin = m_screenExtents.GetMinX() + xOffset - 6.0f;
|
|
float xMax = xMin + width - 3.0f;
|
|
float yMin = m_screenExtents.GetMinY() - 6.0f;
|
|
float yMax = yMin + (m_screenExtents.GetHeight()*0.333f);
|
|
|
|
selectedListBL.x = xMin;
|
|
selectedListBL.y = yMax;
|
|
selectedListBR.x = xMax;
|
|
selectedListBR.y = yMax;
|
|
|
|
grcColor(animSceneEditor->GetColor(hasFocus ? CAnimSceneEditor::kFocusTextOutlineColor : CAnimSceneEditor::kSelectedTextOutlineColor));
|
|
grcBegin(drawLineStrip, 4);
|
|
grcVertex2f(xMin, yMax);
|
|
grcVertex2f(xMin, yMin);
|
|
grcVertex2f(xMax, yMin);
|
|
grcVertex2f(xMax, yMax);
|
|
grcEnd();
|
|
}
|
|
|
|
xOffset += width;
|
|
}
|
|
|
|
xOffset = m_scrollOffset;
|
|
|
|
// render the currently selected sections in a row.
|
|
CAnimSceneSectionIterator it(*pScene);
|
|
bool hasSections = false;
|
|
float lastXMid = -FLT_MAX;
|
|
s32 index = 0;
|
|
|
|
float yMin = m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.333f;
|
|
float yMax = m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.666f;
|
|
float totalSectionsWidth = 0.f;
|
|
|
|
while (*it)
|
|
{
|
|
CAnimSceneSection::Id id = it.GetId();
|
|
|
|
if (id!=m_draggedSection)
|
|
{
|
|
float width = GetTextWidth(id.GetCStr()) + spacing;
|
|
float xMid = m_screenExtents.GetMinX() + xOffset + (GetTextWidth(id.GetCStr())*0.5f);
|
|
float textPadding = 3.0f;
|
|
|
|
if (IsDraggingSection() && mouseX>=lastXMid && mouseX<xMid)
|
|
{
|
|
hoveredSectionIndex = index;
|
|
xOffset+=GetTextWidth(m_draggedSection.GetCStr()) + spacing;
|
|
}
|
|
|
|
bool isHovering = (mouseX>=m_screenExtents.GetMinX() + xOffset) && (mouseX<=m_screenExtents.GetMinX() + xOffset + GetTextWidth(id.GetCStr()))
|
|
&& (mouseY>=yMin - textPadding) && (mouseY<=yMin + textPadding);
|
|
bool displayingMasterList = (GetSelectedPlaybackList()==ms_InvalidPlaybackListId);
|
|
bool isSelected = displayingMasterList && m_selectedSection.GetHash()==id.GetHash();
|
|
|
|
RenderTextWithBackground(id.GetCStr(), m_screenExtents.GetMinX() + xOffset, yMin,
|
|
animSceneEditor->GetColor(isHovering ? CAnimSceneEditor::kSelectedTextHoverColor : isSelected ? CAnimSceneEditor::kSelectedTextColor : CAnimSceneEditor::kMainTextColor),
|
|
animSceneEditor->GetColor(isSelected ? CAnimSceneEditor::kSelectedTextBackGroundColor :CAnimSceneEditor::kTextBackgroundColor), textPadding, true,
|
|
animSceneEditor->GetColor(isSelected ? CAnimSceneEditor::kSelectedTextOutlineColor :CAnimSceneEditor::kTextOutlineColor));
|
|
|
|
// start dragging or select sections for delete as appropriate
|
|
if (isHovering && leftMouseDown && !animSceneEditor->IsDragging())
|
|
{
|
|
if (displayingMasterList)
|
|
{
|
|
// when displaying the master list, allow selecting sections for deletion
|
|
m_selectedSection = id;
|
|
animSceneEditor->SetFocus(CAnimSceneEditor::kFocusSection);
|
|
}
|
|
else
|
|
{
|
|
// when showing a playlist, allow dragging sections out of the list
|
|
m_dragStartTime = fwTimer::GetTimeInMilliseconds();
|
|
m_draggedSection = id;
|
|
m_flags.SetFlag(kDraggingSectionFromPlaybackList);
|
|
}
|
|
}
|
|
|
|
lastXMid = xMid;
|
|
hasSections = true;
|
|
xOffset += width;
|
|
totalSectionsWidth += width;
|
|
index++;
|
|
}
|
|
|
|
++it;
|
|
}
|
|
|
|
if (!hasSections)
|
|
{
|
|
atHashString str("Drag sections here to add them to the list");
|
|
float yMin = m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.333f;
|
|
float yMax = m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.666f;
|
|
bool isHovering = (mouseX>=m_screenExtents.GetMinX() + xOffset) && (mouseX<=m_screenExtents.GetMinX() + xOffset + GetTextWidth(str.GetCStr()))
|
|
&& (mouseY>=yMin) && (mouseY<=yMax);
|
|
|
|
RenderText(str.GetCStr(), m_screenExtents.GetMinX() + xOffset, m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.333f,
|
|
animSceneEditor->GetColor(isHovering ? CAnimSceneEditor::kTextWarningColor : CAnimSceneEditor::kTextWarningColor));
|
|
|
|
xOffset = GetTextWidth(str.GetCStr());
|
|
}
|
|
|
|
// Draw a connected border around the section list for the selected playback list
|
|
if (m_selectedList!=ANIM_SCENE_PLAYBACK_LIST_ID_INVALID)
|
|
{
|
|
float xMin = m_screenExtents.GetMinX() + m_scrollOffset;
|
|
float xMax = totalSectionsWidth + xMin; // m_screenExtents.GetMaxX();
|
|
|
|
grcColor(animSceneEditor->GetColor(playbackListHasFocus ? CAnimSceneEditor::kFocusTextOutlineColor : CAnimSceneEditor::kSelectedTextOutlineColor));
|
|
grcBegin(drawLineStrip, 6);
|
|
grcVertex2f(selectedListBL.x, selectedListBL.y);
|
|
grcVertex2f(xMin-6.0f, yMin-6.0f);
|
|
grcVertex2f(xMin-6.0f, yMax-6.0f);
|
|
grcVertex2f(xMax-6.0f, yMax-6.0f);
|
|
grcVertex2f(xMax-6.0f, yMin-6.0f);
|
|
grcVertex2f(selectedListBR.x, selectedListBR.y);
|
|
grcEnd();
|
|
}
|
|
|
|
|
|
// Render the master list of sections
|
|
if (GetSelectedPlaybackList()!=ms_InvalidPlaybackListId)
|
|
{
|
|
if (IsDraggingSection())
|
|
{
|
|
// render the dragged section at the mouse pointer
|
|
RenderTextWithBackground(m_draggedSection.GetCStr(), mouseX, mouseY,
|
|
animSceneEditor->GetColor( CAnimSceneEditor::kSelectedTextHoverColor),
|
|
animSceneEditor->GetColor( CAnimSceneEditor::kSelectedTextBackGroundColor), 3.0f, true,
|
|
animSceneEditor->GetColor( CAnimSceneEditor::kSelectedTextOutlineColor));
|
|
|
|
if(!m_scrollbar.IsBarHidden())
|
|
{
|
|
if(mouseX > m_screenExtents.GetMaxX() - 10.f)
|
|
{
|
|
float amount = mouseX - m_screenExtents.GetMaxX() + 5.f;
|
|
m_scrollbar.ScrollPositiveAmount(amount);
|
|
m_scrollOffset = -m_scrollbar.GetValue();
|
|
}
|
|
else if (mouseX < m_screenExtents.GetMinX() + 10.f)
|
|
{
|
|
float amount = m_screenExtents.GetMinX() - mouseX + 5.f;
|
|
m_scrollbar.ScrollNegativeAmount(amount);
|
|
m_scrollOffset = -m_scrollbar.GetValue();
|
|
}
|
|
}
|
|
|
|
|
|
if (!leftMouseDown)
|
|
{
|
|
static u32 s_ClickTime = 150;
|
|
if ((fwTimer::GetTimeInMilliseconds() - m_dragStartTime) < s_ClickTime)
|
|
{
|
|
// set the scene time to the start of the
|
|
animSceneEditor->GetScene()->Skip((animSceneEditor->GetScene()->GetSection(m_draggedSection)->GetStart()));
|
|
}
|
|
|
|
// TODO - check if we're over the list pane and add the section to the list
|
|
float yMin = m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.2f;
|
|
float yMax = m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.666f;
|
|
bool isHovering = (mouseX>=(m_screenExtents.GetMinX() - 30.0f)) && (mouseX<=m_screenExtents.GetMaxX())
|
|
&& (mouseY>=yMin) && (mouseY<=yMax);
|
|
|
|
if (isHovering && m_flags.IsFlagSet(kDraggingSectionFromMasterList))
|
|
{
|
|
animSceneEditor->GetScene()->RemoveSectionFromPlaybackList(m_draggedSection, m_selectedList);
|
|
animSceneEditor->GetScene()->AddSectionToPlaybackList(m_draggedSection, m_selectedList, hoveredSectionIndex);
|
|
}
|
|
else if (m_flags.IsFlagSet(kDraggingSectionFromPlaybackList))
|
|
{
|
|
if (!isHovering)
|
|
{
|
|
animSceneEditor->GetScene()->RemoveSectionFromPlaybackList(m_draggedSection, m_selectedList);
|
|
}
|
|
else
|
|
{
|
|
// reorder the entry in the list
|
|
animSceneEditor->GetScene()->RemoveSectionFromPlaybackList(m_draggedSection, m_selectedList);
|
|
animSceneEditor->GetScene()->AddSectionToPlaybackList(m_draggedSection, m_selectedList, hoveredSectionIndex);
|
|
}
|
|
}
|
|
|
|
m_draggedSection = ms_InvalidSectionId;
|
|
m_flags.ClearFlag(kDraggingSectionFromMasterList);
|
|
m_flags.ClearFlag(kDraggingSectionFromPlaybackList);
|
|
m_dragStartTime = 0;
|
|
}
|
|
}
|
|
|
|
// render all the sections in a row.
|
|
float offset = m_scrollOffset;//0.0f;
|
|
const float spacing = 15.0f;
|
|
CAnimSceneSectionIterator it(*pScene, true);
|
|
while (*it)
|
|
{
|
|
CAnimSceneSection::Id id = it.GetId();
|
|
float width = GetTextWidth(id.GetCStr()) + spacing;
|
|
float yMin = m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.666f;
|
|
float yMax = m_screenExtents.GetMaxY();
|
|
bool isDisabled = IsDraggingSection() || animSceneEditor->GetScene()->ContainsSection(id);
|
|
bool isHovering = !isDisabled && (mouseX>=m_screenExtents.GetMinX() + offset) && (mouseX<=m_screenExtents.GetMinX() + offset + GetTextWidth(id.GetCStr()))
|
|
&& (mouseY>=yMin) && (mouseY<=yMax);
|
|
|
|
RenderTextWithBackground(id.GetCStr(), m_screenExtents.GetMinX() + offset, m_screenExtents.GetMinY() + m_screenExtents.GetHeight()*0.666f,
|
|
animSceneEditor->GetColor( isDisabled ? CAnimSceneEditor::kDisabledTextColor : isHovering ? CAnimSceneEditor::kSelectedTextHoverColor : CAnimSceneEditor::kMainTextColor),
|
|
animSceneEditor->GetColor( isDisabled ? CAnimSceneEditor::kDisabledBackgroundColor : isHovering ? CAnimSceneEditor::kSelectedTextBackGroundColor : CAnimSceneEditor::kTextBackgroundColor), 3.0f, true,
|
|
animSceneEditor->GetColor( isDisabled ? CAnimSceneEditor::kDisabledOutlineColor : isHovering ? CAnimSceneEditor::kSelectedTextOutlineColor : CAnimSceneEditor::kTextOutlineColor));
|
|
|
|
// start dragging if appropriate
|
|
if ( isHovering && leftMouseDown && !animSceneEditor->IsDragging() && !IsDraggingScrollbar())
|
|
{
|
|
m_dragStartTime = fwTimer::GetTimeInMilliseconds();
|
|
m_draggedSection = id;
|
|
m_flags.SetFlag(kDraggingSectionFromMasterList);
|
|
animSceneEditor->SetFocus(CAnimSceneEditor::kFocusSection);
|
|
}
|
|
|
|
offset += width;
|
|
++it;
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
COnScreenTimeline::COnScreenTimeline()
|
|
: m_currentTime(0.0f)
|
|
, m_minSelectableTime(0.0f)
|
|
, m_maxSelectableTime(1000.0f)
|
|
, m_lastMouseX(0.0f)
|
|
, m_timeMode(kDisplayFrames)
|
|
, m_bMarkerSnapToFrames(true)
|
|
, m_timelineSelectorDraggedCB(NULL)
|
|
{
|
|
|
|
}
|
|
|
|
COnScreenTimeline::COnScreenTimeline(const CScreenExtents& screenExtents)
|
|
: m_currentTime(0.0f)
|
|
, m_minSelectableTime(0.0f)
|
|
, m_maxSelectableTime(1000.0f)
|
|
, m_lastMouseX(0.0f)
|
|
, m_timeMode(kDisplayFrames)
|
|
, m_bMarkerSnapToFrames(true)
|
|
, m_timelineSelectorDraggedCB(NULL)
|
|
{
|
|
m_screenExtents = screenExtents;
|
|
}
|
|
|
|
COnScreenTimeline::~COnScreenTimeline()
|
|
{
|
|
|
|
}
|
|
|
|
// PURPOSE: Call once per frame to update the timeline
|
|
void COnScreenTimeline::Process()
|
|
{
|
|
// Duration of a single frame
|
|
static float fFrameDuration = 1.0f / 30.0f;
|
|
|
|
float mouseX = static_cast<float>(ioMouse::GetX());
|
|
float mouseY = static_cast<float>(ioMouse::GetY());
|
|
float invZoom = 1.0f/ m_zoomController.m_fZoom;
|
|
|
|
// Extents of the entire timeline - bar and text
|
|
const float xMin = m_screenExtents.GetMinX();
|
|
const float xMax = m_screenExtents.GetMaxX();
|
|
const float yMin = m_screenExtents.GetMinY();
|
|
const float yMax = m_screenExtents.GetMaxY();
|
|
const float timelineWidth = xMax - xMin;
|
|
|
|
static float minimumTimeLineHeight = 25.0f; // We don't want it too thin
|
|
|
|
// Arrow for when current selected time is off either end of the timeline
|
|
static float fArrowWidth = 10.0f; // Width of arrow when it is off the left or right of the timeline
|
|
static float fArrowGap = 3.0f; // Gap to the left/right sides of the timeline between it and the arrow.
|
|
|
|
// Timeline bar itself
|
|
float timelineMinY = yMin;
|
|
float timelineMaxY = yMax;
|
|
|
|
if ((timelineMaxY - timelineMinY) < minimumTimeLineHeight)
|
|
{
|
|
timelineMaxY = timelineMinY + minimumTimeLineHeight;
|
|
}
|
|
|
|
float timelineHeight = timelineMaxY - timelineMinY;
|
|
|
|
// Limit mouse hovering to the timeline itself
|
|
CScreenExtents timelineExtents(xMin, timelineMinY, xMax, timelineMaxY);
|
|
bool mouseHovering = timelineExtents.Contains(mouseX,mouseY);
|
|
|
|
// Is the mouseHovering over the areas of the arrows at either end?
|
|
CScreenExtents leftArrowExtents(xMin - fArrowWidth - fArrowGap, timelineMinY, xMin, timelineMaxY);
|
|
CScreenExtents rightArrowExtents(xMax, timelineMinY, xMax + fArrowWidth + fArrowGap, timelineMaxY);
|
|
bool mouseHoveringLeftArrow = leftArrowExtents.Contains(mouseX, mouseY);
|
|
bool mouseHoveringRightArrow = rightArrowExtents.Contains(mouseX, mouseY);
|
|
|
|
// Should we render the current frame label? Only do this when dragging
|
|
bool bRenderCurrentFrameLabel = false;
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Update
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
if (!m_flags.IsFlagSet(kUserControlDisabled))
|
|
{
|
|
if (m_flags.IsFlagSet(kDraggingSelector))
|
|
{
|
|
// selector dragging mode
|
|
m_flags.ClearFlag(kDraggingTimeline);
|
|
if (ioMouse::GetButtons() & ioMouse::MOUSE_LEFT)
|
|
{
|
|
// update the selected time by the mouse x movement
|
|
float dt = (mouseX - m_lastMouseX) * invZoom;
|
|
|
|
float fNewTime = GetCurrentTime() + dt;
|
|
SetCurrentTime(Clamp(fNewTime, GetMinVisibleTime(), GetMaxVisibleTime()));
|
|
|
|
// As we drag the marker around, show the helper current frame label
|
|
bRenderCurrentFrameLabel = true;
|
|
}
|
|
else
|
|
{
|
|
// Upon stopping dragging of the marker, should it snap to the start of the frame boundary?
|
|
if (m_bMarkerSnapToFrames)
|
|
{
|
|
int iFrameNumber = (int)(GetCurrentTime() / (1.0f/30.0f));
|
|
float fNewTime = (float)iFrameNumber * (1.0f/30.0f);
|
|
|
|
// If past half-way point of a frame, round up instead...
|
|
if ((GetCurrentTime() - fNewTime) >= (0.5f * (1.0f/30.0f)))
|
|
{
|
|
fNewTime = (float)(iFrameNumber + 1) * (1.0f/30.0f);
|
|
}
|
|
|
|
SetCurrentTime(fNewTime);
|
|
}
|
|
|
|
m_flags.ClearFlag(kDraggingSelector);
|
|
}
|
|
|
|
// Time changed due to dragging selector callback
|
|
if (m_timelineSelectorDraggedCB)
|
|
{
|
|
m_timelineSelectorDraggedCB(GetCurrentTime());
|
|
}
|
|
}
|
|
else if (m_flags.IsFlagSet(kDraggingTimeline))
|
|
{
|
|
// Timeline dragging mode
|
|
if (ioMouse::GetButtons() & ioMouse::MOUSE_LEFT)
|
|
{
|
|
m_zoomController.UpdateZoom(xMin, xMax, mouseX, this);
|
|
}
|
|
else
|
|
{
|
|
m_flags.ClearFlag(kDraggingTimeline);
|
|
}
|
|
}
|
|
else if (ioMouse::GetButtons() & ioMouse::MOUSE_LEFT )
|
|
{
|
|
// free mouse mode
|
|
if (IsHoveringSelector())
|
|
{
|
|
m_flags.SetFlag(kDraggingSelector);
|
|
}
|
|
else if (mouseHovering)
|
|
{
|
|
m_flags.SetFlag(kDraggingTimeline);
|
|
}
|
|
else if ((mouseHoveringLeftArrow && GetCurrentTime() < GetMinVisibleTime()) || (mouseHoveringRightArrow && GetCurrentTime() > GetMaxVisibleTime()))
|
|
{
|
|
MoveMarkerToVisibleTimelinePosition(0.5f);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
// update just the zooming control for the timeline
|
|
m_zoomController.UpdateZoom(xMin, xMax, mouseX, this, true);
|
|
}
|
|
}
|
|
|
|
// Clamp timeline offset to keep it visible
|
|
ClampTimelineOffset();
|
|
|
|
// Calculate some information we'll use throughout
|
|
const float timelineStartTime = GetMinVisibleTime();
|
|
const float timelineEndTime = GetMaxVisibleTime();
|
|
const float timelineRangeTime = timelineEndTime - timelineStartTime;
|
|
|
|
const int timelineStartFrame = (int)(ceil(timelineStartTime / fFrameDuration));
|
|
const int timelineEndFrame = (int)(ceil(timelineEndTime / fFrameDuration));
|
|
|
|
const int numVisibleFrames = timelineEndFrame - timelineStartFrame;
|
|
float fPixelsPerFrame = 1.0f;
|
|
if (numVisibleFrames > 0)
|
|
{
|
|
fPixelsPerFrame = timelineWidth / (float)numVisibleFrames;
|
|
}
|
|
|
|
const float timelineMinSelectableTime = timelineStartTime < m_minSelectableTime ? m_minSelectableTime : timelineStartTime;
|
|
const int timelineMinSelectableFrame = (int)(ceil(timelineMinSelectableTime / fFrameDuration));
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render - Timeline Bar & End of selectable range lines
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
// Render the timeline to the screen at the specified extents
|
|
grcLighting(false);
|
|
|
|
bool bStartOfSelectableRangeIsInView = (m_minSelectableTime >= timelineStartTime && m_minSelectableTime <= timelineEndTime);
|
|
float fStartOfSelectableRangeTimelineX = bStartOfSelectableRangeIsInView ? GetScreenX(m_minSelectableTime) : xMin;
|
|
|
|
bool bEndOfSelectableRangeIsInView = (m_maxSelectableTime >= timelineStartTime && m_maxSelectableTime <= timelineEndTime);
|
|
float fEndOfSelectableRangeTimelineX = bEndOfSelectableRangeIsInView ? GetScreenX(m_maxSelectableTime) : xMax;
|
|
|
|
// Render timeline dark background
|
|
grcColor(GetColor(kTimelineBackgroundInRangeColor));
|
|
grcBegin(drawTriStrip, 4);
|
|
{
|
|
grcVertex2f(fStartOfSelectableRangeTimelineX, timelineMinY);
|
|
grcVertex2f(fEndOfSelectableRangeTimelineX, timelineMinY);
|
|
grcVertex2f(fStartOfSelectableRangeTimelineX, timelineMaxY);
|
|
grcVertex2f(fEndOfSelectableRangeTimelineX, timelineMaxY);
|
|
}
|
|
grcEnd();
|
|
|
|
// Render even darker background before the range of the selectable range
|
|
if (bStartOfSelectableRangeIsInView)
|
|
{
|
|
grcColor(GetColor(kTimelineBackgroundOutOfRangeColor));
|
|
grcBegin(drawTriStrip, 4);
|
|
{
|
|
grcVertex2f(xMin, timelineMinY);
|
|
grcVertex2f(fStartOfSelectableRangeTimelineX, timelineMinY);
|
|
grcVertex2f(xMin, timelineMaxY);
|
|
grcVertex2f(fStartOfSelectableRangeTimelineX, timelineMaxY);
|
|
}
|
|
grcEnd();
|
|
}
|
|
|
|
// Render even darker background beyond the range of the selectable range
|
|
if (bEndOfSelectableRangeIsInView)
|
|
{
|
|
grcColor(GetColor(kTimelineBackgroundOutOfRangeColor));
|
|
grcBegin(drawTriStrip, 4);
|
|
{
|
|
grcVertex2f(fEndOfSelectableRangeTimelineX, timelineMinY);
|
|
grcVertex2f(xMax, timelineMinY);
|
|
grcVertex2f(fEndOfSelectableRangeTimelineX, timelineMaxY);
|
|
grcVertex2f(xMax, timelineMaxY);
|
|
}
|
|
grcEnd();
|
|
}
|
|
|
|
// White for outlines
|
|
grcColor(GetColor(kTimelineOutlineColor));
|
|
|
|
// Render a solid white line, top to bottom at the start of the scene.
|
|
if (bStartOfSelectableRangeIsInView)
|
|
{
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(fStartOfSelectableRangeTimelineX, timelineMinY);
|
|
grcVertex2f(fStartOfSelectableRangeTimelineX, timelineMaxY);
|
|
grcEnd();
|
|
}
|
|
|
|
// Render a solid white line, top to bottom at the end of the scene.
|
|
if (bEndOfSelectableRangeIsInView)
|
|
{
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(fEndOfSelectableRangeTimelineX, timelineMinY);
|
|
grcVertex2f(fEndOfSelectableRangeTimelineX, timelineMaxY);
|
|
grcEnd();
|
|
}
|
|
|
|
// Render timeline white outline
|
|
grcBegin(drawLineStrip, 5);
|
|
grcVertex2f(xMin, timelineMinY);
|
|
grcVertex2f(xMax, timelineMinY);
|
|
grcVertex2f(xMax, timelineMaxY);
|
|
grcVertex2f(xMin, timelineMaxY);
|
|
grcVertex2f(xMin, timelineMinY);
|
|
grcEnd();
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render - Timeline Bar - Time Markers
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
static float fTimeMarkerHeight30 = 0.5f * timelineHeight; // Largest marker for every 30 frame (1 second) mark
|
|
static float fTimeMarkerHeight5 = 0.35f * timelineHeight;
|
|
static float fTimeMarkerHeight1 = 0.2f * timelineHeight; // Smallest marker for every 1 frame mark
|
|
|
|
static float fMinimumTimeMarkerGap = 3.0f; // Minimum gap allowed between time markers
|
|
|
|
// Should we render the smaller markers?
|
|
bool bRender1FrameMarkers = (fPixelsPerFrame > fMinimumTimeMarkerGap);
|
|
bool bRender5FrameMarkers = ((5.0f * fPixelsPerFrame) > fMinimumTimeMarkerGap);
|
|
|
|
// Optimisation: If we know we're not rendering the smaller frame markers, then we can avoid going over every frame in the below for loop
|
|
int iMarkerStartFrame = timelineMinSelectableFrame;
|
|
int iMarkerJumpAmount = 1;
|
|
|
|
if (!bRender5FrameMarkers)
|
|
{
|
|
// We won't be rendering the 5 or 1 frame markers here, so the for-loop increments should be to the 30 frame markers
|
|
iMarkerJumpAmount = 30;
|
|
if (iMarkerStartFrame % 30 != 0)
|
|
{
|
|
iMarkerStartFrame = iMarkerStartFrame + (30 - (iMarkerStartFrame % 30));
|
|
}
|
|
}
|
|
else if (!bRender1FrameMarkers)
|
|
{
|
|
// We won't be rendering the 1 frame markers here, so the for-loop increments should be to the 5 frame markers
|
|
iMarkerJumpAmount = 5;
|
|
if (iMarkerStartFrame % 5 != 0)
|
|
{
|
|
iMarkerStartFrame = iMarkerStartFrame + (5 - (iMarkerStartFrame % 5));
|
|
}
|
|
}
|
|
|
|
// Render the markers
|
|
for (int i = iMarkerStartFrame; i < timelineEndFrame; i += iMarkerJumpAmount)
|
|
{
|
|
// Don't render markers beyond the end of the selectable timeline.
|
|
float fMarkerTime = i * fFrameDuration;
|
|
if (fMarkerTime >= m_maxSelectableTime)
|
|
{
|
|
break;
|
|
}
|
|
|
|
// X position of the marker to be rendered
|
|
float markerPointX = GetScreenX(fMarkerTime);
|
|
|
|
// Don't render 1-frame time markers where we'll be rendering larger ones.
|
|
if (bRender1FrameMarkers && i % 5 != 0 && i % 30 != 0)
|
|
{
|
|
grcColor(GetColor(kTimelineTimeMarker1FrameColor));
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(markerPointX, timelineMinY + fTimeMarkerHeight1);
|
|
grcVertex2f(markerPointX, timelineMinY);
|
|
grcEnd();
|
|
}
|
|
else if (bRender5FrameMarkers && i % 5 == 0 && i % 30 != 0)
|
|
{
|
|
grcColor(GetColor(kTimelineTimeMarker5FrameColor));
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(markerPointX, timelineMinY + fTimeMarkerHeight5);
|
|
grcVertex2f(markerPointX, timelineMinY);
|
|
grcEnd();
|
|
}
|
|
else if (i % 30 == 0)
|
|
{
|
|
grcColor(GetColor(kTimelineTimeMarker30FrameColor));
|
|
grcBegin(drawLineStrip, 2);
|
|
grcVertex2f(markerPointX, timelineMinY + fTimeMarkerHeight30);
|
|
grcVertex2f(markerPointX, timelineMinY);
|
|
grcEnd();
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render - Timeline Bar - Time Markers - Text
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
// How many frames does the timeline represent?
|
|
int iNumFramesVisible = (int)(timelineRangeTime / fFrameDuration);
|
|
|
|
const int idealNumberOfLabels = 12;
|
|
int iFramesBetweenLabels = iNumFramesVisible / idealNumberOfLabels;
|
|
|
|
if (iFramesBetweenLabels >= 25 && iFramesBetweenLabels % 30 != 0)
|
|
{
|
|
// Round it up to a multiple of 30
|
|
iFramesBetweenLabels += (30 - (iFramesBetweenLabels % 30));
|
|
}
|
|
else if (iFramesBetweenLabels % 5 != 0)
|
|
{
|
|
// Round it up to a multiple of 5
|
|
iFramesBetweenLabels += (5 - (iFramesBetweenLabels % 5));
|
|
}
|
|
|
|
// What's the first label to render?
|
|
int iFirstLabelFrame = timelineMinSelectableFrame;
|
|
if (iFirstLabelFrame % iFramesBetweenLabels != 0)
|
|
{
|
|
iFirstLabelFrame = iFirstLabelFrame + (iFramesBetweenLabels - (iFirstLabelFrame % iFramesBetweenLabels));
|
|
}
|
|
|
|
const float fLabelY = timelineMinY + fTimeMarkerHeight30;
|
|
|
|
for (int i = iFirstLabelFrame; i < timelineEndFrame; i += iFramesBetweenLabels)
|
|
{
|
|
// Don't render labels beyond the end of the selectable timeline.
|
|
float fLabelTime = i * fFrameDuration;
|
|
if (fLabelTime >= m_maxSelectableTime)
|
|
{
|
|
break;
|
|
}
|
|
|
|
float fLabelX = GetScreenX(fLabelTime);
|
|
|
|
// Generate the label
|
|
atString labelString;
|
|
if (m_timeMode == kDisplayFrames)
|
|
{
|
|
atVarString label("%d", i);
|
|
labelString = label;
|
|
|
|
}
|
|
else if (m_timeMode == kDisplayTimes)
|
|
{
|
|
atVarString label("%.2f", fLabelTime);
|
|
labelString = label;
|
|
}
|
|
|
|
// Do not render the label if it's off the end of the timeline
|
|
float fLabelWidth = GetTextWidth(labelString.c_str());
|
|
if ((fLabelX + fLabelWidth) < xMax)
|
|
{
|
|
RenderText(labelString.c_str(), fLabelX, fLabelY, GetColor(kTimelineTimeMarkerLabelColor));
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render - Timeline Selector and Arrows
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
float selectedScreenX = GetScreenX(GetCurrentTime());
|
|
|
|
// Selector arrow visible when the current selected time is within the visible timeline
|
|
static float fSelectorArrowGap = 3.0f; // Space at the top and bottom between the selector arrow and the timeline bar edges.
|
|
static float fSelectorWidth = 5.0f;
|
|
|
|
const float fArrowTopY = timelineMinY + fSelectorArrowGap;
|
|
const float fArrowBottomY = timelineMaxY - fSelectorArrowGap;
|
|
const float fArrowMidY = fArrowTopY + ((fArrowBottomY - fArrowTopY) * 0.5f);
|
|
|
|
if (selectedScreenX < xMin)
|
|
{
|
|
// Render a left arrow.
|
|
grcColor(mouseHoveringLeftArrow ? GetColor(kTimelineSelectorHoverColor) : GetColor(kTimelineSelectorColor));
|
|
grcBegin(drawTris, 3);
|
|
grcVertex2f(xMin - fArrowGap, fArrowTopY);
|
|
grcVertex2f(xMin - fArrowGap, fArrowBottomY);
|
|
grcVertex2f(xMin - fArrowWidth - fArrowGap, fArrowMidY);
|
|
grcEnd();
|
|
}
|
|
else if (selectedScreenX > xMax)
|
|
{
|
|
// Render a right arrow.
|
|
grcColor(mouseHoveringRightArrow ? GetColor(kTimelineSelectorHoverColor) : GetColor(kTimelineSelectorColor));
|
|
grcBegin(drawTris, 3);
|
|
grcVertex2f(xMax + fArrowGap, fArrowTopY);
|
|
grcVertex2f(xMax + fArrowWidth + fArrowGap, fArrowMidY);
|
|
grcVertex2f(xMax + fArrowGap, fArrowBottomY);
|
|
grcEnd();
|
|
}
|
|
else
|
|
{
|
|
// Render a triangle selector for the current selected time.
|
|
grcColor(GetColor(kTimelineBackgroundOutOfRangeColor));
|
|
//render a black outline
|
|
grcBegin(drawTris, 3);
|
|
grcVertex2f(selectedScreenX - fSelectorWidth - 1.0f, timelineMaxY - fSelectorArrowGap + 1.0f);
|
|
grcVertex2f(selectedScreenX + fSelectorWidth + 1.0f, timelineMaxY - fSelectorArrowGap + 1.0f);
|
|
grcVertex2f(selectedScreenX, timelineMinY + 0.5f);
|
|
grcEnd();
|
|
|
|
if (m_flags.IsFlagSet(kDraggingSelector))
|
|
{
|
|
grcColor(GetColor(kTimelineSelectorDraggingColor));
|
|
}
|
|
else if (IsHoveringSelector())
|
|
{
|
|
grcColor(GetColor(kTimelineSelectorHoverColor));
|
|
}
|
|
else
|
|
{
|
|
grcColor(GetColor(kTimelineSelectorColor));
|
|
}
|
|
grcBegin(drawTris, 3);
|
|
grcVertex2f(selectedScreenX - fSelectorWidth, timelineMaxY - fSelectorArrowGap);
|
|
grcVertex2f(selectedScreenX + fSelectorWidth, timelineMaxY - fSelectorArrowGap);
|
|
grcVertex2f(selectedScreenX, timelineMinY + 1.0f);
|
|
grcEnd();
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Render - Current Selector Time
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
if (bRenderCurrentFrameLabel)
|
|
{
|
|
// Lower text position Y
|
|
float selectorTimeTextY = timelineMinY + fTimeMarkerHeight30;
|
|
|
|
atString selectorTimeStr;
|
|
|
|
if (m_timeMode == kDisplayFrames)
|
|
{
|
|
int iFrameNumber = int(m_currentTime / fFrameDuration);
|
|
atVarString str("%d", iFrameNumber);
|
|
selectorTimeStr = str;
|
|
}
|
|
else if (m_timeMode == kDisplayTimes)
|
|
{
|
|
atVarString str("%.2f", m_currentTime);
|
|
selectorTimeStr = str;
|
|
}
|
|
|
|
float fStringWidth = GetTextWidth(selectorTimeStr.c_str());
|
|
float fStringPosX = GetScreenX(m_currentTime);
|
|
fStringPosX -= (0.5f * fStringWidth);
|
|
|
|
fStringPosX = Clamp(fStringPosX, xMin, xMax - fStringWidth);
|
|
RenderTextWithBackground(selectorTimeStr.c_str(), fStringPosX, selectorTimeTextY, GetColor(kTimelineSelectorTimeTextColor), GetColor(kTimelineSelectorTimeBackgroundColor));
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Remember any values for next update
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
m_lastMouseX = mouseX;
|
|
}
|
|
|
|
void COnScreenTimeline::SetColor(u32 colorType, Color32 color)
|
|
{
|
|
if (colorType < kTimelineColor_MaxNum)
|
|
{
|
|
m_colors[colorType] = color;
|
|
}
|
|
}
|
|
|
|
|
|
Color32 COnScreenTimeline::GetColor(eColorType type)
|
|
{
|
|
if (type < kTimelineColor_MaxNum)
|
|
{
|
|
return m_colors[type];
|
|
}
|
|
|
|
return Color32(0,0,0,0);
|
|
|
|
/*
|
|
|
|
switch (type)
|
|
{
|
|
case COnScreenTimeline::kTimelineSelectorColor:
|
|
return Color32(160, 160, 160, 160);
|
|
case COnScreenTimeline::kTimelineSelectorHoverColor:
|
|
return Color32(255, 255, 255, 160);
|
|
case COnScreenTimeline::kTimelineSelectorDraggingColor:
|
|
return Color32(255, 0, 0, 160);
|
|
case COnScreenTimeline::kTimelineSelectorTimeTextColor:
|
|
return Color32(0, 0, 0, 128);
|
|
case COnScreenTimeline::kTimelineSelectorTimeBackgroundColor:
|
|
return Color32(128, 128, 128, 128);
|
|
case COnScreenTimeline::kTimelineOutlineColor:
|
|
return Color32(128, 128, 128, 128);
|
|
case COnScreenTimeline::kTimelineBackgroundInRangeColor:
|
|
return Color32(0, 0, 0, 128);
|
|
case COnScreenTimeline::kTimelineBackgroundOutOfRangeColor:
|
|
return Color32(0, 0, 0, 160);
|
|
case COnScreenTimeline::kTimelineTimeMarkerLabelColor:
|
|
return Color32(128, 128, 128, 128);
|
|
case COnScreenTimeline::kTimelineTimeMarker1FrameColor:
|
|
return Color32(64, 64, 64, 128);
|
|
case COnScreenTimeline::kTimelineTimeMarker5FrameColor:
|
|
return Color32(96, 96, 96, 128);
|
|
case COnScreenTimeline::kTimelineTimeMarker30FrameColor:
|
|
return Color32(128, 128, 128, 128);
|
|
|
|
default:
|
|
return Color32(0,0,0,0);
|
|
}
|
|
*/
|
|
}
|
|
|
|
void COnScreenTimeline::ClampTimelineOffset()
|
|
{
|
|
float invZoom = 1.0f / m_zoomController.m_fZoom;
|
|
float timelineWidth = m_screenExtents.GetMaxX() - m_screenExtents.GetMinX();
|
|
float timelineTimeRange = timelineWidth * invZoom;
|
|
float fMinimumTimelineStartTime = m_minSelectableTime - timelineTimeRange;
|
|
|
|
// Don't go below the minimum range
|
|
if (m_zoomController.m_fTimeLineOffset > -(fMinimumTimelineStartTime * m_zoomController.m_fZoom))
|
|
{
|
|
m_zoomController.m_fTimeLineOffset = -(fMinimumTimelineStartTime * m_zoomController.m_fZoom);
|
|
}
|
|
|
|
// Don't go above the maximum range
|
|
if (m_zoomController.m_fTimeLineOffset < (-m_maxSelectableTime * m_zoomController.m_fZoom))
|
|
{
|
|
m_zoomController.m_fTimeLineOffset = (-m_maxSelectableTime * m_zoomController.m_fZoom);
|
|
}
|
|
}
|
|
|
|
void COnScreenTimeline::TimeLineZoom::CalculateInitialZoom(float xMin, float xMax, float fRangeStart, float fRangeEnd)
|
|
{
|
|
float fRange = fRangeEnd - fRangeStart;
|
|
if (fRange < 0.01f)
|
|
{
|
|
m_fZoom = 10.0f;
|
|
return;
|
|
}
|
|
|
|
// Initially display the range as approx 90% of the timeline
|
|
fRange *= 1.1f;
|
|
|
|
float fTimelineWidth = xMax - xMin;
|
|
|
|
m_fZoom = fTimelineWidth / fRange;
|
|
m_fTimeLineOffset = 0;
|
|
}
|
|
|
|
void COnScreenTimeline::TimeLineZoom::UpdateZoom(float xMin, float xMax, float fMouse, COnScreenTimeline* owningTimeline, bool bZoomOnly /*=false*/)
|
|
{
|
|
Assert(owningTimeline);
|
|
if (ioMouse::HasWheel() && (ioMouse::GetDZ()!=0))
|
|
{
|
|
// Get the time at the mouse position
|
|
float timeAtMousePos = owningTimeline->GetTimeForScreenX(fMouse);
|
|
|
|
// Update zoom
|
|
const float kMouseZoomFactor = 1.25f;
|
|
m_fZoom *= ioMouse::GetDZ() > 0 ? kMouseZoomFactor : 1.0f / kMouseZoomFactor;
|
|
m_fZoom = Clamp(m_fZoom, 1.0f, 1000.0f);
|
|
|
|
// Get how far the mouse is along the timeline as a ratio.
|
|
float fMousePosXRatio = (fMouse - xMin) / (xMax - xMin);
|
|
|
|
// Get the range of the timeline
|
|
float fTimelineRange = owningTimeline->GetMaxVisibleTime() - owningTimeline->GetMinVisibleTime();
|
|
|
|
// Calculate the time the start of the timeline needs to be in order to keep the same time at the mouse position post zoom.
|
|
float fNewTimelineStartTime = timeAtMousePos - (fTimelineRange * fMousePosXRatio);
|
|
|
|
// Now work out the offset required to put the start time there
|
|
m_fTimeLineOffset = -(fNewTimelineStartTime * m_fZoom);
|
|
}
|
|
else if (ioMouse::GetButtons() & ioMouse::MOUSE_LEFT && !bZoomOnly)
|
|
{
|
|
if (m_LastMouseTrackFrame == (TIME.GetFrameCount() - 1))
|
|
{
|
|
float fDeltaX = fMouse - m_fLastMouseX;
|
|
m_fTimeLineOffset += fDeltaX;
|
|
}
|
|
|
|
m_LastMouseTrackFrame = TIME.GetFrameCount();
|
|
m_fLastMouseX = fMouse;
|
|
}
|
|
}
|
|
|
|
void COnScreenTimeline::CalculateInitialZoom(float fRangeStart, float fRangeEnd)
|
|
{
|
|
const float xMin = m_screenExtents.GetMinX();
|
|
const float xMax = m_screenExtents.GetMaxX();
|
|
|
|
m_zoomController.CalculateInitialZoom(xMin, xMax, fRangeStart, fRangeEnd);
|
|
}
|
|
|
|
float COnScreenTimeline::GetSelectorVisualPosition()
|
|
{
|
|
const float fTimelineRange = GetMaxVisibleTime() - GetMinVisibleTime();
|
|
const float fSelectorCurrentTime = GetCurrentTime();
|
|
|
|
const float fSelectorPos = fSelectorCurrentTime - GetMinVisibleTime();
|
|
|
|
return fSelectorPos / fTimelineRange;
|
|
}
|
|
|
|
void COnScreenTimeline::MoveMarkerToVisibleTimelinePosition(float fPositionOnVisibleTimeline)
|
|
{
|
|
const float fTimelineRange = GetMaxVisibleTime() - GetMinVisibleTime();
|
|
|
|
// Calculate the time the start of the timeline needs to be in order to put the current time in the centre
|
|
const float fNewTimelineStartTime = GetCurrentTime() - (fTimelineRange * fPositionOnVisibleTimeline);
|
|
|
|
// Now work out the offset required to put the new start time there
|
|
m_zoomController.m_fTimeLineOffset = -(fNewTimelineStartTime * m_zoomController.m_fZoom);
|
|
|
|
ClampTimelineOffset();
|
|
}
|
|
|
|
float COnScreenTimeline::GetScreenX(float time)
|
|
{
|
|
float minTime = GetMinVisibleTime();
|
|
float maxTime = GetMaxVisibleTime();
|
|
|
|
float n = (time - minTime) / (maxTime-minTime);
|
|
|
|
return Lerp(n, m_screenExtents.GetMinX(), m_screenExtents.GetMaxX());
|
|
}
|
|
|
|
float COnScreenTimeline::GetTimeForScreenX(float x)
|
|
{
|
|
float n = (x - m_screenExtents.GetMinX()) / (m_screenExtents.GetMaxX() - m_screenExtents.GetMinX());
|
|
|
|
n = Clamp(n, 0.0f, 1.0f);
|
|
return Lerp(n, GetMinVisibleTime(), GetMaxVisibleTime());
|
|
}
|
|
|
|
float COnScreenTimeline::GetMinVisibleTime()
|
|
{
|
|
float invZoom = 1.0f/m_zoomController.m_fZoom;
|
|
|
|
return -(m_zoomController.m_fTimeLineOffset*invZoom);
|
|
}
|
|
|
|
float COnScreenTimeline::GetMaxVisibleTime()
|
|
{
|
|
float invZoom = 1.0f/m_zoomController.m_fZoom;
|
|
float timelineWidth = m_screenExtents.GetMaxX() - m_screenExtents.GetMinX();
|
|
return GetMinVisibleTime()+(timelineWidth*invZoom);
|
|
}
|
|
|
|
// PURPOSE: Set the screen extents of the timeline control
|
|
void COnScreenTimeline::SetScreenExtents(const CScreenExtents& screenExtents)
|
|
{
|
|
m_screenExtents = screenExtents;
|
|
}
|
|
|
|
bool COnScreenTimeline::IsHoveringSelector()
|
|
{
|
|
static float s_selectorTolerance = 5.0f;
|
|
float mouseX = static_cast<float>(ioMouse::GetX());
|
|
float mouseY = static_cast<float>(ioMouse::GetY());
|
|
if (mouseY>=m_screenExtents.GetMinY() && mouseY<=m_screenExtents.GetMaxY())
|
|
{
|
|
if (Abs(mouseX - GetScreenX(GetCurrentTime()))<s_selectorTolerance)
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
CAnimSceneEditor::CAnimSceneEditor()
|
|
: m_pScene(NULL)
|
|
, m_pickerSettings(NULL)
|
|
{
|
|
SetAnimScene(NULL);
|
|
m_widgets.Init();
|
|
|
|
// Editor setting defaults
|
|
m_editorSettingTimelinePlaybackMode = kTimelinePlaybackMode_Static;
|
|
m_editorSettingTimelineDisplayMode = kTimelineDisplayMode_Frames;
|
|
m_editorSettingTimelineSnapToFrames = true;
|
|
m_fSelectorTimelinePositionUponPlayback = 0.5f;
|
|
m_editorSettingEventEditorSnapToFrames = true;
|
|
m_editorSettingEditEventPreloads = false;
|
|
m_editorSettingPauseSceneAtFirstStart = true;
|
|
m_editorSettingResetSceneOnPlaybackListChange = true;
|
|
m_editorSettingAutoRegisterPlayer = false;
|
|
|
|
m_EventLayersYScreenOffset = 22.0f;
|
|
}
|
|
|
|
// Constructor. Set the extents of the editor on screen
|
|
CAnimSceneEditor::CAnimSceneEditor(CAnimScene* pScene, const CScreenExtents& screenExtents)
|
|
: m_pScene(NULL)
|
|
, m_pickerSettings(NULL)
|
|
{
|
|
Init(pScene, screenExtents);
|
|
}
|
|
|
|
CAnimSceneEditor::~CAnimSceneEditor()
|
|
{
|
|
// cleanup
|
|
}
|
|
|
|
|
|
void CAnimSceneEditor::SetEditorAndComponentColors()
|
|
{
|
|
SetVideoControlPanelColors();
|
|
SetAuthoringHelperColors();
|
|
SetAnimSceneEditorColors();
|
|
SetTimelinePanelColors();
|
|
}
|
|
|
|
void CAnimSceneEditor::SetVideoControlPanelColors()
|
|
{
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlBackgroundColor, ASE_Panel_BackGroundColor);
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlDisplayOutlineColor, ASE_Panel_OutlineColor);
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlButtonColor, ASE_Panel_Button_Color);
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlHoverButtonColor, ASE_Panel_Button_HoverColor);
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlActiveButtonColor, ASE_Panel_Button_ActiveColor);
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlActiveButtonHighLigtColor, ASE_Panel_Button_ActiveHoverColor);
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlActiveButtonBackgroundColor, ASE_Panel_Button_ActiveBackgroundColor);
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlPanelButtonOutlineColor, ASE_Panel_Button_ActiveOutlineColor);
|
|
m_videoPlayBackControl.SetColor(COnScreenVideoControl::kVideoControlPanelActiveButtonOutlineColor, ASE_Panel_Button_OutlineColor);
|
|
|
|
}
|
|
|
|
void CAnimSceneEditor::SetTimelinePanelColors()
|
|
{
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineSelectorColor, ASE_Panel_Button_Color);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineSelectorHoverColor, ASE_Panel_Button_HoverColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineSelectorDraggingColor, ASE_Panel_Button_ActiveOutlineColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineSelectorTimeTextColor, ASE_Panel_BackGroundColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineSelectorTimeBackgroundColor, ASE_Panel_Button_HoverColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineTimeMarkerLabelColor, ASE_Panel_OutlineColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineOutlineColor, ASE_Panel_OutlineColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineBackgroundInRangeColor, ASE_Panel_BackGroundColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineBackgroundOutOfRangeColor, ASE_Panel_BackGroundColorDark);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineTimeMarker1FrameColor, ASE_Timeline_Marker1FrameColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineTimeMarker5FrameColor, ASE_Timeline_Marker5FrameColor);
|
|
m_timeline.SetColor(COnScreenTimeline::kTimelineTimeMarker30FrameColor, ASE_Timeline_Marker30FrameColor);
|
|
}
|
|
|
|
|
|
void CAnimSceneEditor::InitVideoControlPanel()
|
|
{
|
|
if(m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStepToStart))
|
|
{
|
|
m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStepToStart)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::StepToStartCB));
|
|
}
|
|
|
|
if(m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStepBackwards))
|
|
{
|
|
m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStepBackwards)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::StepBackwardCB));
|
|
}
|
|
|
|
if(m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStop))
|
|
{
|
|
m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStop)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::StopCB));
|
|
}
|
|
|
|
if(m_videoPlayBackControl.GetButton(COnScreenVideoControl::kPlayBackwards))
|
|
{
|
|
m_videoPlayBackControl.GetButton(COnScreenVideoControl::kPlayBackwards)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::PlaySceneBackwardsCB));
|
|
}
|
|
|
|
if(m_videoPlayBackControl.GetButton(COnScreenVideoControl::kPlayForwards))
|
|
{
|
|
m_videoPlayBackControl.GetButton(COnScreenVideoControl::kPlayForwards)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::PlaySceneForwardsCB));
|
|
}
|
|
|
|
if(m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStepForwards))
|
|
{
|
|
m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStepForwards)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::StepForwardCB));
|
|
}
|
|
|
|
if(m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStepToEnd))
|
|
{
|
|
m_videoPlayBackControl.GetButton(COnScreenVideoControl::kStepToEnd)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::StepToEndCB));
|
|
}
|
|
|
|
SetVideoControlPanelColors();
|
|
}
|
|
|
|
void CAnimSceneEditor::SetAuthoringHelperColors()
|
|
{
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlPanelBackgroundColor, ASE_Panel_BackGroundColor);
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlPanelOutlineColor, ASE_Panel_OutlineColor);
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlButtonColor, ASE_Panel_Button_Color);
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlHoverButtonColor, ASE_Panel_Button_HoverColor);
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlActiveButtonColor, ASE_Panel_Button_ActiveColor);
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlActiveButtonHighLigtColor, ASE_Panel_Button_ActiveHoverColor);
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlActiveButtonBackgroundColor, ASE_Panel_Button_ActiveBackgroundColor);
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlPanelActiveButtonOutlineColor, ASE_Panel_Button_ActiveOutlineColor);
|
|
m_authoringDisplay.SetColor(CAuthoringHelperDisplay::kVideoControlPanelButtonOutlineColor, ASE_Panel_Button_OutlineColor);
|
|
|
|
}
|
|
|
|
void CAnimSceneEditor::InitAuthoringHelperPanel()
|
|
{
|
|
if(m_authoringDisplay.GetButton(CAuthoringHelperDisplay::kTransGbl))
|
|
{
|
|
m_authoringDisplay.GetButton(CAuthoringHelperDisplay::kTransGbl)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::SetAuthoringHelperTransGbl));
|
|
}
|
|
|
|
if(m_authoringDisplay.GetButton(CAuthoringHelperDisplay::kTransLcl))
|
|
{
|
|
m_authoringDisplay.GetButton(CAuthoringHelperDisplay::kTransLcl)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::SetAuthoringHelperTransLcl));
|
|
}
|
|
|
|
if(m_authoringDisplay.GetButton(CAuthoringHelperDisplay::kRotLcl))
|
|
{
|
|
m_authoringDisplay.GetButton(CAuthoringHelperDisplay::kRotLcl)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::SetAuthoringHelperRotLcl));
|
|
}
|
|
|
|
if(m_authoringDisplay.GetButton(CAuthoringHelperDisplay::kRotGbl))
|
|
{
|
|
m_authoringDisplay.GetButton(CAuthoringHelperDisplay::kRotGbl)->SetButtonCallBack(MakeFunctorRet(*this, &CAnimSceneEditor::SetAuthoringHelperRotGbl));
|
|
}
|
|
|
|
SetAuthoringHelperColors();
|
|
}
|
|
|
|
void CAnimSceneEditor::InitScenePicker()
|
|
{
|
|
//if(!g_PickerManager.IsEnabled())
|
|
//{
|
|
// g_PickerManager.SetEnabled(true);
|
|
// g_PickerManager.SetUiEnabled(false);
|
|
//}
|
|
|
|
//if(!m_pickerSettings)
|
|
//{
|
|
// m_pickerSettings = rage_new CGtaPickerInterfaceSettings();
|
|
//}
|
|
|
|
//m_pickerSettings->m_bShowHideEnabled = false;
|
|
//m_pickerSettings->m_ShowHideMode = PICKER_SHOW_ALL;
|
|
|
|
//g_PickerManager.SetPickerInterfaceSettings(m_pickerSettings);
|
|
|
|
//g_PickerManager.TakeControlOfPickerWidget("Anim Scenes");
|
|
//g_PickerManager.ResetList(true);
|
|
}
|
|
|
|
void CAnimSceneEditor::Init(CAnimScene* pScene, const CScreenExtents& screenExtents)
|
|
{
|
|
//InitColours();
|
|
SetAnimScene(pScene);
|
|
CheckAnimSceneVersion();
|
|
SetScreenExtents(screenExtents);
|
|
|
|
m_pickerSettings = NULL;
|
|
|
|
m_timeline.SetTimelineSelectorDraggedCallback(MakeFunctor(*this, &CAnimSceneEditor::TimelineSelectorDragged));
|
|
m_timeline.CalculateInitialZoom(0.0f, pScene ? pScene->GetDuration() : 0.0f);
|
|
|
|
InitVideoControlPanel();
|
|
InitAuthoringHelperPanel();
|
|
SetAnimSceneEditorColors();
|
|
SetTimelinePanelColors();
|
|
|
|
m_widgets.Init();
|
|
|
|
InitScenePicker();
|
|
|
|
InitEntityInitialisers();
|
|
InitEventInitialisers();
|
|
InitEventScrollbar();
|
|
m_firstPlayback = true;
|
|
}
|
|
|
|
void CAnimSceneEditor::Widgets::Init()
|
|
{
|
|
m_pSelectionGroup = NULL;
|
|
m_pAddEntityGroup = NULL;
|
|
m_pSaveStatus = NULL;
|
|
m_pSaveButton = NULL;
|
|
m_pCloseButton = NULL;
|
|
m_pEntityTypeCombo = NULL;
|
|
m_selectedEntityType=0;
|
|
m_newEntityId.SetHash(0);
|
|
// m_boolValue = false;
|
|
m_pEventTypeCombo = NULL;
|
|
m_selectedEventType = 0;
|
|
m_pAddEventGroup = NULL;
|
|
m_pAddSectionGroup = NULL;
|
|
m_pSceneGroup = NULL;
|
|
/* m_useEntityClipSelector = false;*/
|
|
}
|
|
|
|
void CAnimSceneEditor::Shutdown()
|
|
{
|
|
CleanupEventInitialiserWidgets();
|
|
CleanupEntityInitialiserWidgets();
|
|
if(m_pScene)
|
|
{
|
|
m_pScene->ShutdownWidgets();
|
|
}
|
|
m_widgets.Shutdown();
|
|
m_selected.SelectEntity(NULL);
|
|
m_selected.SelectEvent(NULL);
|
|
if (m_pScene)
|
|
CAnimSceneManager::BankDestroyAnimScene(m_pScene);
|
|
SetAnimScene(NULL);
|
|
m_flags.ClearAllFlags();
|
|
|
|
if(m_pickerSettings)
|
|
{
|
|
delete m_pickerSettings;
|
|
|
|
m_pickerSettings = NULL;
|
|
}
|
|
|
|
for (s32 i=0; i<m_eventInitialisers.GetCount(); i++)
|
|
{
|
|
delete m_eventInitialisers[i];
|
|
m_eventInitialisers[i] = NULL;
|
|
}
|
|
m_eventInitialisers.clear();
|
|
|
|
for (s32 i=0; i<m_entityInitialisers.GetCount(); i++)
|
|
{
|
|
delete m_entityInitialisers[i];
|
|
m_entityInitialisers[i] = NULL;
|
|
}
|
|
m_entityInitialisers.clear();
|
|
m_firstPlayback = true;
|
|
}
|
|
|
|
void CAnimSceneEditor::Widgets::Shutdown()
|
|
{
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Shut down the Selected group
|
|
//////////////////////////////////////////////////////////////////////////
|
|
m_playbackListLeadInClipSetSelector.RemoveWidgets();
|
|
|
|
if (m_pSelectionGroup)
|
|
{
|
|
m_pSelectionGroup->Destroy();
|
|
}
|
|
m_pSelectionGroup = NULL;
|
|
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Shut down the add event group (widgets first)
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
m_addEventSectionSelector.SetAnimScene(NULL);
|
|
m_addEventSectionSelector.RemoveWidgets();
|
|
|
|
if (m_pEventTypeCombo)
|
|
{
|
|
m_pEventTypeCombo->Destroy();
|
|
}
|
|
m_pEventTypeCombo = NULL;
|
|
|
|
if (m_pAddEventGroup)
|
|
{
|
|
m_pAddEventGroup->Destroy();
|
|
}
|
|
m_pAddEventGroup = NULL;
|
|
|
|
m_selectedEventType = 0;
|
|
m_eventNameList.clear();
|
|
|
|
if (m_pAddSectionGroup)
|
|
{
|
|
m_pAddSectionGroup->Destroy();
|
|
}
|
|
m_pAddSectionGroup = NULL;
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Shut down the add entity group (widgets first)
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
if (m_pEntityTypeCombo)
|
|
{
|
|
m_pEntityTypeCombo->Destroy();
|
|
}
|
|
m_pEntityTypeCombo = NULL;
|
|
|
|
if (m_pAddEntityGroup)
|
|
{
|
|
m_pAddEntityGroup->Destroy();
|
|
}
|
|
m_pAddEntityGroup = NULL;
|
|
|
|
m_selectedEntityType=0;
|
|
m_entityNameList.clear();
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
// Remove the core widgets
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
if (m_pSceneGroup)
|
|
{
|
|
m_pSceneGroup->Destroy();
|
|
}
|
|
m_pSceneGroup = NULL;
|
|
|
|
if (m_pSaveStatus)
|
|
{
|
|
m_pSaveStatus->Destroy();
|
|
}
|
|
m_pSaveStatus = NULL;
|
|
|
|
if (m_pSaveButton)
|
|
{
|
|
m_pSaveButton->Destroy();
|
|
}
|
|
m_pSaveButton = NULL;
|
|
|
|
if (m_pCloseButton)
|
|
{
|
|
m_pCloseButton->Destroy();
|
|
}
|
|
m_pCloseButton = NULL;
|
|
}
|
|
|
|
void CAnimSceneEditor::SyncPickerFromAnimSceneEntity()
|
|
{
|
|
CAnimSceneEntity* AnimSceneEntity = GetSelectedEntity();
|
|
|
|
if(AnimSceneEntity)
|
|
{
|
|
CEntity* pEnt = m_pScene->GetPhysicalEntity(AnimSceneEntity->GetId(), false); ;
|
|
if(AnimSceneEntity->GetType() == ANIM_SCENE_ENTITY_PED )
|
|
{
|
|
pEnt = static_cast<CAnimScenePed*>(AnimSceneEntity)->GetPed(false);
|
|
}
|
|
else if(AnimSceneEntity->GetType() == ANIM_SCENE_ENTITY_VEHICLE )
|
|
{
|
|
pEnt = static_cast<CAnimSceneVehicle*>(AnimSceneEntity)->GetVehicle(false);
|
|
}
|
|
else if (AnimSceneEntity->GetType() == ANIM_SCENE_ENTITY_OBJECT )
|
|
{
|
|
pEnt = static_cast<CAnimSceneObject*>(AnimSceneEntity)->GetObject(false);
|
|
}
|
|
|
|
g_PickerManager.AddEntityToPickerResults(pEnt, true, true);
|
|
}
|
|
};
|
|
|
|
void CAnimSceneEditor::RenderSelectedAnimScenesPossibleNewGameEntity()
|
|
{
|
|
CEntity* pickerEntity = static_cast<CEntity*>(g_PickerManager.GetEntity(0));
|
|
if(pickerEntity)
|
|
{
|
|
if(GetSelectedEntity())
|
|
{
|
|
CEntity* pEnt = m_pScene->GetPhysicalEntity(GetSelectedEntity()->GetId(), false);
|
|
|
|
if(pEnt && pEnt != pickerEntity)
|
|
{
|
|
if(pickerEntity->GetIsTypePed() == pEnt->GetIsTypePed()
|
|
|| pickerEntity->GetIsTypeObject() == pEnt->GetIsTypeObject()
|
|
|| pickerEntity->GetIsTypeVehicle() == pEnt->GetIsTypeVehicle())
|
|
{
|
|
char name[128];
|
|
formatf(name, "register to %s", GetSelectedEntity()->GetId().GetCStr());
|
|
grcDebugDraw::Text(pickerEntity->GetTransform().GetPosition(), GetColor(kSelectedTextColor), name, true);
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::OnGameEntityRegister()
|
|
{
|
|
if(m_pScene)
|
|
{
|
|
m_pScene->Stop();
|
|
m_pScene->Reset();
|
|
}
|
|
}
|
|
|
|
bool CAnimSceneEditor::PlaySceneForwardsCB(u32 buttonState)
|
|
{
|
|
if(m_pScene)
|
|
{
|
|
float rate = m_pScene->GetRate();
|
|
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
if( m_pScene->IsFinished())
|
|
{
|
|
m_pScene->Reset();
|
|
}
|
|
else if ( m_pScene->GetDuration() <= m_pScene->GetTimeWithSkipping() )
|
|
{
|
|
m_pScene->Skip(0.f);
|
|
}
|
|
m_pScene->SetPaused(false);
|
|
|
|
if(rate < 0.0f)
|
|
{
|
|
m_pScene->SetRate(rate * -1.0f);
|
|
}
|
|
|
|
// Remember the selector position when we play
|
|
m_fSelectorTimelinePositionUponPlayback = m_timeline.GetSelectorVisualPosition();
|
|
|
|
return true;
|
|
}
|
|
|
|
if(buttonState == COnScreenButton::kButtonReleased)
|
|
{
|
|
m_pScene->SetPaused(true);
|
|
return false;
|
|
}
|
|
|
|
if(buttonState == COnScreenButton::kButtonHeld)
|
|
{
|
|
if(!m_pScene->IsPlayingBack() || m_pScene->GetPaused() || rate < 0.0f)
|
|
{
|
|
return false;
|
|
}
|
|
|
|
if(m_pScene->GetDuration() <= m_pScene->GetTimeWithSkipping())
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
}
|
|
|
|
return false;
|
|
};
|
|
|
|
bool CAnimSceneEditor::PlaySceneBackwardsCB(u32 buttonState)
|
|
{
|
|
if(m_pScene)
|
|
{
|
|
float rate = m_pScene->GetRate();
|
|
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
m_pScene->SetPaused(false);
|
|
|
|
if(rate > 0.0f)
|
|
{
|
|
m_pScene->SetRate(rate * -1.0f);
|
|
}
|
|
|
|
// Remember the selector position when we play
|
|
m_fSelectorTimelinePositionUponPlayback = m_timeline.GetSelectorVisualPosition();
|
|
|
|
return true;
|
|
}
|
|
|
|
if(buttonState == COnScreenButton::kButtonReleased)
|
|
{
|
|
if(!m_pScene->GetPaused())
|
|
{
|
|
m_pScene->SetPaused(true);
|
|
|
|
}
|
|
return false;
|
|
}
|
|
|
|
if(buttonState == COnScreenButton::kButtonHeld)
|
|
{
|
|
if(!m_pScene->IsPlayingBack() || m_pScene->GetPaused() || rate > 0.0f)
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
}
|
|
|
|
return false;
|
|
};
|
|
|
|
bool CAnimSceneEditor::StepForwardCB(u32 buttonState)
|
|
{
|
|
const float SINGLE_FRAME_DURATION = (1.0f / 30.0f);
|
|
|
|
if(m_pScene)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
/*
|
|
if( m_pScene->IsFinished() || (m_pScene->GetDuration() <= m_pScene->GetTimeWithSkipping()) )
|
|
{
|
|
m_pScene->Reset();
|
|
m_pScene->SetPaused(true);
|
|
return false;
|
|
}*/
|
|
|
|
m_pScene->SetPaused(true);
|
|
float newTime = m_pScene->GetTime();
|
|
|
|
if (m_editorSettingTimelineSnapToFrames)
|
|
{
|
|
int iCurrentFrame = (int)(newTime / SINGLE_FRAME_DURATION);
|
|
newTime = (float)(iCurrentFrame + 1) * SINGLE_FRAME_DURATION;
|
|
}
|
|
else
|
|
{
|
|
newTime += SINGLE_FRAME_DURATION;
|
|
}
|
|
|
|
m_pScene->Skip(newTime);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return false;
|
|
|
|
};
|
|
|
|
bool CAnimSceneEditor::StepBackwardCB(u32 buttonState)
|
|
{
|
|
const float SINGLE_FRAME_DURATION = (1.0f / 30.0f);
|
|
|
|
if(m_pScene)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
m_pScene->SetPaused(true);
|
|
float newTime = m_pScene->GetTime();
|
|
|
|
if (m_editorSettingTimelineSnapToFrames)
|
|
{
|
|
int iCurrentFrame = (int)(newTime / SINGLE_FRAME_DURATION);
|
|
float fCurrentFrameTime = (float)(iCurrentFrame) * SINGLE_FRAME_DURATION;
|
|
|
|
if (newTime - fCurrentFrameTime < 0.001f)
|
|
{
|
|
newTime = (float)(iCurrentFrame - 1) * SINGLE_FRAME_DURATION;
|
|
}
|
|
else
|
|
{
|
|
newTime = (float)(iCurrentFrame) * SINGLE_FRAME_DURATION;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
newTime -= SINGLE_FRAME_DURATION;
|
|
}
|
|
|
|
m_pScene->Skip(newTime);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return false;
|
|
|
|
};
|
|
|
|
bool CAnimSceneEditor::StepToStartCB(u32 buttonState)
|
|
{
|
|
if(m_pScene)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
if(m_pScene->IsFinished())
|
|
{
|
|
m_pScene->Reset();
|
|
m_pScene->SetPaused(true);
|
|
return false;
|
|
}
|
|
else
|
|
{
|
|
m_pScene->SetPaused(true);
|
|
m_pScene->Skip(0.0f);
|
|
return false;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return false;
|
|
|
|
};
|
|
|
|
bool CAnimSceneEditor::StepToEndCB(u32 buttonState)
|
|
{
|
|
if(m_pScene)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
m_pScene->SetPaused(true);
|
|
m_pScene->Skip(m_pScene->GetDuration());
|
|
}
|
|
}
|
|
else
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return false;
|
|
|
|
};
|
|
|
|
bool CAnimSceneEditor::StopCB(u32 buttonState)
|
|
{
|
|
if(m_pScene)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
m_pScene->SetPaused(true);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return false;
|
|
|
|
};
|
|
|
|
bool CAnimSceneEditor::SetAuthoringHelperTransGbl(u32 buttonState)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
CAuthoringHelper::SetAuthoringMode(CAuthoringHelper::TRANS_GBL);
|
|
return true;
|
|
}
|
|
|
|
if(buttonState == COnScreenButton::kButtonReleased)
|
|
{
|
|
CAuthoringHelper::SetAuthoringMode(CAuthoringHelper::NO_AUTHOR_MODE);
|
|
return false;
|
|
}
|
|
|
|
if(CAuthoringHelper::GetCurrentAuthoringMode() == CAuthoringHelper::TRANS_GBL && buttonState == COnScreenButton::kButtonHeld)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
bool CAnimSceneEditor::SetAuthoringHelperTransLcl(u32 buttonState)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
CAuthoringHelper::SetAuthoringMode(CAuthoringHelper::TRANS_LCL);
|
|
return true;
|
|
}
|
|
|
|
if(buttonState == COnScreenButton::kButtonReleased)
|
|
{
|
|
CAuthoringHelper::SetAuthoringMode(CAuthoringHelper::NO_AUTHOR_MODE);
|
|
return false;
|
|
}
|
|
|
|
if(CAuthoringHelper::GetCurrentAuthoringMode() == CAuthoringHelper::TRANS_LCL && buttonState == COnScreenButton::kButtonHeld)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
bool CAnimSceneEditor::SetAuthoringHelperRotGbl(u32 buttonState)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
CAuthoringHelper::SetAuthoringMode(CAuthoringHelper::ROT_GBL);
|
|
return true;
|
|
}
|
|
|
|
if(buttonState == COnScreenButton::kButtonReleased)
|
|
{
|
|
CAuthoringHelper::SetAuthoringMode(CAuthoringHelper::NO_AUTHOR_MODE);
|
|
return false;
|
|
}
|
|
|
|
if(CAuthoringHelper::GetCurrentAuthoringMode() == CAuthoringHelper::ROT_GBL && buttonState == COnScreenButton::kButtonHeld)
|
|
{
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
bool CAnimSceneEditor::SetAuthoringHelperRotLcl(u32 buttonState)
|
|
{
|
|
if(buttonState == COnScreenButton::kButtonPressed)
|
|
{
|
|
CAuthoringHelper::SetAuthoringMode(CAuthoringHelper::ROT_LCL);
|
|
return true;
|
|
}
|
|
|
|
if(buttonState == COnScreenButton::kButtonReleased)
|
|
{
|
|
CAuthoringHelper::SetAuthoringMode(CAuthoringHelper::NO_AUTHOR_MODE);
|
|
return false;
|
|
}
|
|
|
|
if(CAuthoringHelper::GetCurrentAuthoringMode() == CAuthoringHelper::ROT_LCL && buttonState == COnScreenButton::kButtonHeld)
|
|
{
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
|
|
bool CAnimSceneEditor::IsSelectingADifferentGameEntity()
|
|
{
|
|
CEntity* hoverEnt = static_cast<CEntity*>(g_PickerManager.GetHoverEntity());
|
|
|
|
if(hoverEnt)
|
|
{
|
|
//set the current anim scene physical entity
|
|
for(int i=0; i < m_pScene->GetNumEntities(); i++)
|
|
{
|
|
CAnimSceneEntity* localAnimSceneEntity = m_pScene->GetEntity(i);
|
|
|
|
if(localAnimSceneEntity->GetId())
|
|
{
|
|
CEntity* pEnt = m_pScene->GetPhysicalEntity(localAnimSceneEntity->GetId(), false);
|
|
|
|
if(pEnt && pEnt == hoverEnt)
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
if(GetSelectedEntity())
|
|
{
|
|
CEntity* pEnt = m_pScene->GetPhysicalEntity(GetSelectedEntity()->GetId(), false);
|
|
|
|
if(hoverEnt && pEnt)
|
|
{
|
|
if(pEnt != hoverEnt)
|
|
{
|
|
if(pEnt->GetIsTypePed() && hoverEnt->GetIsTypePed())
|
|
{
|
|
return true;
|
|
}
|
|
else if (pEnt->GetIsTypeVehicle() && hoverEnt->GetIsTypeVehicle())
|
|
{
|
|
return true;
|
|
}
|
|
else if (pEnt->GetIsTypeObject() && hoverEnt->GetIsTypeObject())
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
void CAnimSceneEditor::SyncAnimSceneEntityFromPicker()
|
|
{
|
|
if(GetScene() && ((ioMouse::GetReleasedButtons() & ioMouse::MOUSE_LEFT) || (ioMouse::GetButtons() & ioMouse::MOUSE_LEFT)))
|
|
{
|
|
if(g_PickerManager.IsEnabled())
|
|
{
|
|
CEntity* pickerEnt = static_cast<CEntity*>(g_PickerManager.GetEntity(0));
|
|
|
|
//set the current anim scene physical entity
|
|
for(int i=0; i < m_pScene->GetNumEntities(); i++)
|
|
{
|
|
CAnimSceneEntity* localAnimSceneEntity = m_pScene->GetEntity(i);
|
|
|
|
if(localAnimSceneEntity->GetId())
|
|
{
|
|
CEntity* pEnt = m_pScene->GetPhysicalEntity(localAnimSceneEntity->GetId(), false);
|
|
|
|
if(pEnt && pEnt == pickerEnt)
|
|
{
|
|
SelectEntity(localAnimSceneEntity);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// PURPOSE: Call once per frame to update the editor
|
|
void CAnimSceneEditor::Process_RenderThread()
|
|
{
|
|
if (m_pScene && m_pScene->IsLoaded())
|
|
{
|
|
m_mouseState.Update();
|
|
|
|
//Switch to a 2d display mode
|
|
grcViewport* prevViewport=grcViewport::GetCurrent();
|
|
grcViewport screenViewport;
|
|
|
|
grcViewport::SetCurrent(&screenViewport);
|
|
grcViewport::GetCurrent()->Screen();
|
|
|
|
grcStateBlock::SetBlendState(grcStateBlock::BS_CompositeAlpha);
|
|
grcStateBlock::SetRasterizerState(grcStateBlock::RS_NoBackfaceCull);
|
|
grcStateBlock::SetDepthStencilState(grcStateBlock::DSS_IgnoreDepth);
|
|
|
|
// Render the selected entity
|
|
// TODO: This will need fixing up once we have multiple selection of entities.
|
|
if (m_selected.GetEntity())
|
|
{
|
|
CPhysical* pPhysEnt = m_pScene->GetPhysicalEntity(m_selected.GetEntity()->GetId(), false);
|
|
if (pPhysEnt)
|
|
{
|
|
CDebugScene::DrawEntityBoundingBox(pPhysEnt, ASE_EntityPickerBoundingBoxColor);
|
|
}
|
|
}
|
|
|
|
// Render the version number (top-left)
|
|
grcLighting(false);
|
|
atVarString versionNumber("ANIM SCENE EDITOR (BETA) v%d.%d - %s (ASV%d)",
|
|
ASE_MAJOR_VERSION, ASE_MINOR_VERSION, m_pScene->GetName().TryGetCStr(), m_pScene->GetVersion());
|
|
RenderTextWithBackground(versionNumber.c_str(), m_screenExtents.GetMinX(), m_screenExtents.GetMinY() + 5.0f, ASE_VersionColor,
|
|
ASE_Panel_BackGroundColor, 3.0f, true, ASE_Panel_OutlineColor);
|
|
|
|
m_sectionPanel.Render(this);
|
|
|
|
if (m_flags.IsFlagSet(kDraggingEvent))
|
|
{
|
|
m_timeline.DisableUserControl();
|
|
}
|
|
else
|
|
{
|
|
m_timeline.EnableUserControl();
|
|
}
|
|
|
|
// keep the selectable range on the timeline synced to the scene duration
|
|
m_timeline.SetSelectableRange(0.0f, m_pScene->GetDuration());
|
|
|
|
// render the timeline
|
|
m_timeline.Process();
|
|
|
|
// render the scene information display
|
|
m_sceneInfoDisplay.Process(m_timeline.GetCurrentTime(), m_pScene->GetDuration());
|
|
|
|
// Event pointers in the event layers need to be reset every frame
|
|
InitEventLayers();
|
|
|
|
// render the events (also fills out the event layers)
|
|
m_pScene->SceneEditorRender(*this);
|
|
|
|
// remove any layers that contain no events
|
|
CullEmptyEventLayers();
|
|
|
|
// render the event layers
|
|
if(!m_editorSettingHideEvents)
|
|
{
|
|
m_EventLayersWindow.Render(this);
|
|
// Render the events scroll bar
|
|
RenderEventsScrollbar();
|
|
}
|
|
|
|
// render the scene playback controls
|
|
m_videoPlayBackControl.Process();
|
|
|
|
m_authoringDisplay.Process();
|
|
|
|
grcViewport::SetCurrent(prevViewport);
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::InitEventLayers()
|
|
{
|
|
// make sure there's a layer for each entity
|
|
for (s32 i=0; i<m_pScene->GetNumEntities(); i++)
|
|
{
|
|
const CAnimSceneEntity* pEnt = m_pScene->GetEntity(i);
|
|
|
|
if (!pEnt)
|
|
{
|
|
return;
|
|
}
|
|
|
|
AddEventLayerIfMissing(pEnt->GetId());
|
|
}
|
|
|
|
AddEventLayerIfMissing(ANIM_SCENE_ENTITY_ID_INVALID);
|
|
|
|
// clear out the stored event pointers before we update
|
|
for (s32 i=0 ; i<m_EventLayersWindow.GetEventLayers().GetCount(); i++)
|
|
{
|
|
if(m_EventLayersWindow.GetEventLayers()[i])
|
|
{
|
|
for (s32 j=0; j< m_EventLayersWindow.GetEventLayers()[i]->GetEventGroup().GetCount(); j++)
|
|
{
|
|
CEventPanelGroup* pGroup = m_EventLayersWindow.GetEventPanelGroup((u32)i,(u32)j);
|
|
if(pGroup)
|
|
{
|
|
pGroup->RemoveAllEvents();
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::AddEventLayerIfMissing(atHashString name)
|
|
{
|
|
bool layerExists = false;
|
|
|
|
for (s32 j=0 ; j<m_EventLayersWindow.GetEventLayers().GetCount(); j++)
|
|
{
|
|
if (m_EventLayersWindow.GetEventLayers()[j]->GetName()==name)
|
|
{
|
|
layerExists = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (!layerExists)
|
|
{
|
|
m_EventLayersWindow.AddEventLayerPanel(name);
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::CullEmptyEventLayers()
|
|
{
|
|
s32 i = m_EventLayersWindow.GetEventLayers().GetCount()-1;
|
|
while (i>-1)
|
|
{
|
|
s32 j=m_EventLayersWindow.GetEventLayers()[i]->GetEventGroup().GetCount()-1;
|
|
while (j>-1)
|
|
{
|
|
CEventPanelGroup* pGroup = m_EventLayersWindow.GetEventPanelGroup((u32)i,(u32)j);
|
|
if(pGroup)
|
|
{
|
|
if(pGroup->GetEvents().GetCount() == 0)
|
|
{
|
|
m_EventLayersWindow.GetEventLayers()[i]->RemoveEventGroup(j);
|
|
}
|
|
}
|
|
//if (m_eventLayers[i].m_subGroups[j].m_events.GetCount()==0)
|
|
//{
|
|
// // cull the sub group
|
|
// m_eventLayers[i].m_subGroups.Delete(j);
|
|
//}
|
|
j--;
|
|
}
|
|
|
|
|
|
|
|
if (m_EventLayersWindow.GetEventLayers()[i]->GetEventGroup().GetCount()==0 && !m_pScene->GetEntity(m_EventLayersWindow.GetEventLayers()[i]->GetName()))
|
|
{
|
|
m_EventLayersWindow.RemoveEventLayerPanel(i);
|
|
}
|
|
|
|
i--;
|
|
}
|
|
}
|
|
|
|
//void CAnimSceneEditor::RenderEventLayers()
|
|
//{
|
|
// TUNE_FLOAT(layerHeight, 15.0f, 0.0f, 100.0f, 1.0f)
|
|
// EventLayer::ms_layerHeight = layerHeight;
|
|
//
|
|
// float height = EventLayer::ms_layerHeight;
|
|
//
|
|
// //static float s_subGroupIndent = 100.0f;
|
|
// m_flags.ClearFlag(kMadeEntitySelectionThisFrame);
|
|
//
|
|
// for (s32 i=0 ; i<GetEventLayers().GetCount(); i++)
|
|
// {
|
|
// CEventLayerPanel& layer = *m_EventLayersWindow.GetEventLayers()[i];
|
|
//
|
|
// bool isSelected = (layer.GetName().GetHash()==GetSelectedEntityId().GetHash());
|
|
//
|
|
// // render the main layer string
|
|
//
|
|
// float mouseX = static_cast<float>(ioMouse::GetX());
|
|
// float mouseY = static_cast<float>(ioMouse::GetY());
|
|
// bool isHovering = false;
|
|
//
|
|
// if (mouseX>=m_EventLayersWindow.GetScreenExtents().GetMinX(), m_EventLayersWindow.GetScreenExtents().GetMinY(), timelineMinX, m_timeline.GetScreenExtents().GetMinY().GetMinX() && mouseX<=(m_EventLayersWindow.GetScreenExtents().GetMinX()+grcFont::GetCurrent().GetStringWidth(layer.GetName().GetCStr(), (s32)strlen(layer.GetName().GetCStr()))))
|
|
// {
|
|
// if (mouseY>=m_EventLayersWindow.GetScreenExtents().GetMinY()+height && mouseY<=(m_EventLayersWindow.GetScreenExtents().GetMinY()+height+grcFont::GetCurrent().GetHeight()))
|
|
// {
|
|
// if (ioMouse::GetButtons() & ioMouse::MOUSE_LEFT && !IsDraggingEvent() && !m_timeline.IsDragging())
|
|
// {
|
|
// SelectEntity(m_pScene->GetEntity(layer.GetName().GetCStr()));
|
|
// m_flags.SetFlag(kMadeEntitySelectionThisFrame);
|
|
// }
|
|
// else
|
|
// {
|
|
// isHovering = true;
|
|
// }
|
|
// }
|
|
// }
|
|
//
|
|
// if(isSelected)
|
|
// {
|
|
// RenderTextWithBackground(layer.GetName().GetCStr(), m_EventLayersWindow.GetScreenExtents().GetMinX(), m_EventLayersWindow.GetScreenExtents().GetMinY()+height,
|
|
// GetColor(isHovering ? kSelectedTextHoverColor : kSelectedTextColor),
|
|
// GetColor(isSelected ? kSelectedTextBackGroundColor :kTextBackgroundColor), 3.0f, true,
|
|
// GetColor(isSelected ? kSelectedTextOutlineColor :kTextOutlineColor));
|
|
// }
|
|
// else
|
|
// {
|
|
// RenderTextWithBackground(layer.GetName().GetCStr(), m_EventLayersWindow.GetScreenExtents().GetMinX(), m_EventLayersWindow.GetScreenExtents().GetMinY()+height,
|
|
// GetColor(isHovering ? kTextHoverColor : kMainTextColor),
|
|
// GetColor(isSelected ? kSelectedTextBackGroundColor :kTextBackgroundColor), 3.0f, true,
|
|
// GetColor(isSelected ? kSelectedTextOutlineColor :kTextOutlineColor));
|
|
// }
|
|
//
|
|
// for (s32 j=0; j<layer.GetEventGroup().GetCount(); j++)
|
|
// {
|
|
// for(s32 k=0; k< layer.GetEventGroup()[j]->GetEvents().GetCount(); k++)
|
|
// {
|
|
// RenderEvent(layer.GetEventGroup()[j]->GetEvents()[k]->GetEventInfo().event, m_EventLayersWindow.GetScreenExtents().GetMinY()+height);
|
|
// }
|
|
//
|
|
// //RenderTextWithBackground(layer.m_subGroups[j].m_name.GetCStr(), m_entityPaneExtents.GetMinX()+s_subGroupIndent, m_entityPaneExtents.GetMinY()+height, textColour,
|
|
// // GetColor(kTextBackgroundColor), 3.0f, false, GetColor(isSelected ? kSelectedTextOutlineColor : kTextOutlineColor));
|
|
// height+=EventLayer::ms_layerHeight;
|
|
// }
|
|
//
|
|
// // make sure we always move down at least one row
|
|
// if (layer.GetEventGroup().GetCount()==0)
|
|
// height+=EventLayer::ms_layerHeight;
|
|
// }
|
|
//}
|
|
|
|
void CAnimSceneEditor::Process_MainThread()
|
|
{
|
|
SyncAnimSceneEntityFromPicker();
|
|
|
|
if (m_flags.IsFlagSet(kCloseCurrentScene))
|
|
{
|
|
Shutdown();
|
|
return;
|
|
}
|
|
|
|
// sync up the playback list if necessary
|
|
if (GetScene() && GetScene()->GetPlayBackList().GetHash() != m_sectionPanel.GetSelectedPlaybackList().GetHash())
|
|
{
|
|
if (m_sectionPanel.SelectedListChangedThisFrame())
|
|
{
|
|
GetScene()->SetPlayBackList(m_sectionPanel.GetSelectedPlaybackList());
|
|
|
|
// This allows us to mimic how script changes playback lists (i.e. no reset on the entire scene).
|
|
if (m_editorSettingResetSceneOnPlaybackListChange)
|
|
{
|
|
GetScene()->Reset();
|
|
GetScene()->SetPaused(true);
|
|
}
|
|
else
|
|
{
|
|
// The playback list has changed, but without a reset the timeline won't adjust to the new range. So force that here.
|
|
m_timeline.CalculateInitialZoom(0.0f, m_pScene->GetDuration());
|
|
}
|
|
|
|
m_widgets.m_addEventSectionSelector.Refresh(); // refresh the section selector to keep it in sync with the current list
|
|
|
|
if (GetSelectedEntity() && GetSelectedEntity()->GetType()==ANIM_SCENE_ENTITY_PED)
|
|
{
|
|
// if we have a selected entity, refresh the lead in clip set drop down to display the correct name
|
|
fwMvClipSetId leadInClipSetId(CLIP_SET_ID_INVALID);
|
|
CAnimScenePed* pPedEnt = static_cast<CAnimScenePed*>(GetSelectedEntity());
|
|
CAnimSceneLeadInData* pData = pPedEnt->FindLeadIn(m_sectionPanel.GetSelectedPlaybackList());
|
|
if (pData)
|
|
{
|
|
leadInClipSetId = pData->m_clipSet.GetId();
|
|
}
|
|
|
|
if (leadInClipSetId==CLIP_SET_ID_INVALID)
|
|
{
|
|
m_widgets.m_playbackListLeadInClipSetSelector.SelectNone();
|
|
}
|
|
else
|
|
{
|
|
m_widgets.m_playbackListLeadInClipSetSelector.Select(leadInClipSetId.GetCStr(), false);
|
|
}
|
|
}
|
|
|
|
m_sectionPanel.GetFlags().ClearFlag(CSectioningPanel::kSelectedListChanged);
|
|
}
|
|
else
|
|
{
|
|
m_sectionPanel.SetSelectedPlaybackList(GetScene()->GetPlayBackList());
|
|
}
|
|
}
|
|
|
|
// // render the debug for the selected entity lead in
|
|
// if (GetScene() && GetSelectedEntity() && GetSelectedEntity()->GetType()==ANIM_SCENE_ENTITY_PED)
|
|
// {
|
|
// fwMvClipSetId leadInClipSetId(CLIP_SET_ID_INVALID);
|
|
// CAnimScenePed* pPedEnt = static_cast<CAnimScenePed*>(GetSelectedEntity());
|
|
// CAnimSceneLeadInData* pData = pPedEnt->FindLeadIn(m_sectionPanel.GetSelectedPlaybackList());
|
|
// if (pData)
|
|
// {
|
|
// leadInClipSetId = pData->m_clipSet.GetId();
|
|
// CMovementTransitionHelper::DebugRenderClipSet(fwClipSetManager::GetClipSet(leadInClipSetId), leadInClipSetId, m_pScene->GetSceneOrigin());
|
|
// }
|
|
// }
|
|
|
|
// Handle dragging and resizing of events
|
|
float mouseX = m_mouseState.m_mouseCoords.x;
|
|
bool leftMouseDown = m_mouseState.m_leftMouseDown;
|
|
bool leftMousePressed = m_mouseState.m_leftMousePressed;
|
|
bool leftMouseReleased = m_mouseState.m_leftMouseReleased;
|
|
|
|
if (m_flags.IsFlagSet(kDraggingEvent) && m_selected.GetEvent())
|
|
{
|
|
if (leftMouseDown)
|
|
{
|
|
// move the selected event by the mouse delta
|
|
float dt = (mouseX - m_mouseState.m_lastMouseCoords.x) * m_timeline.GetScale();
|
|
CAnimSceneEvent* pEvt = m_selected.GetEvent();
|
|
float length = pEvt->GetEnd() - pEvt->GetStart();
|
|
pEvt->SetStart(Clamp(pEvt->GetStart()+dt, 0.0f, m_timeline.GetMaxVisibleTime()));
|
|
pEvt->SetEnd(pEvt->GetStart()+length);
|
|
}
|
|
else
|
|
{
|
|
// Finished dragging event. Snap it to a frame boundary.
|
|
if (m_editorSettingEventEditorSnapToFrames && m_selected.GetEvent())
|
|
{
|
|
CAnimSceneEvent* pEvt = m_selected.GetEvent();
|
|
float length = pEvt->GetEnd() - pEvt->GetStart();
|
|
|
|
int iFrameNumber = (int)(pEvt->GetStart() / (1.0f/30.0f));
|
|
pEvt->SetStart((float)iFrameNumber * (1.0f/30.0f));
|
|
pEvt->SetEnd(pEvt->GetStart()+length);
|
|
}
|
|
|
|
m_flags.ClearFlag(kDraggingEvent);
|
|
}
|
|
}
|
|
else if (m_flags.IsFlagSet(kDraggingEventStart) && m_selected.GetEvent())
|
|
{
|
|
if (leftMouseDown)
|
|
{
|
|
// move the selected event start by the mouse delta
|
|
float dt = (mouseX - m_mouseState.m_lastMouseCoords.x) * m_timeline.GetScale();
|
|
CAnimSceneEvent* pEvt = m_selected.GetEvent();
|
|
pEvt->SetStart(Clamp(pEvt->GetStart()+dt, Max(0.0f, m_timeline.GetMinVisibleTime()), Min(m_timeline.GetMaxVisibleTime(), pEvt->GetEnd())));
|
|
}
|
|
else
|
|
{
|
|
// Finished dragging event. Snap it to a frame boundary.
|
|
if (m_editorSettingEventEditorSnapToFrames && m_selected.GetEvent())
|
|
{
|
|
CAnimSceneEvent* pEvt = m_selected.GetEvent();
|
|
|
|
int iFrameNumber = (int)(pEvt->GetStart() / (1.0f/30.0f));
|
|
pEvt->SetStart((float)iFrameNumber * (1.0f/30.0f));
|
|
}
|
|
|
|
m_flags.ClearFlag(kDraggingEventStart);
|
|
}
|
|
}
|
|
else if (m_flags.IsFlagSet(kDraggingEventEnd) && m_selected.GetEvent())
|
|
{
|
|
if (leftMouseDown)
|
|
{
|
|
// move the selected event end by the mouse delta
|
|
float dt = (mouseX - m_mouseState.m_lastMouseCoords.x) * m_timeline.GetScale();
|
|
CAnimSceneEvent* pEvt = m_selected.GetEvent();
|
|
pEvt->SetEnd(Clamp(pEvt->GetEnd()+dt, Max(pEvt->GetStart(), m_timeline.GetMinVisibleTime()), m_timeline.GetMaxVisibleTime()));
|
|
}
|
|
else
|
|
{
|
|
// Finished dragging event. Snap it to a frame boundary.
|
|
if (m_editorSettingEventEditorSnapToFrames && m_selected.GetEvent())
|
|
{
|
|
CAnimSceneEvent* pEvt = m_selected.GetEvent();
|
|
|
|
int iFrameNumber = (int)(pEvt->GetEnd() / (1.0f/30.0f));
|
|
pEvt->SetEnd((float)iFrameNumber * (1.0f/30.0f));
|
|
}
|
|
|
|
m_flags.ClearFlag(kDraggingEventEnd);
|
|
}
|
|
}
|
|
else if (m_flags.IsFlagSet(kDraggingEventPreLoad) && m_selected.GetEvent())
|
|
{
|
|
if (leftMouseDown)
|
|
{
|
|
// move the selected event by the mouse delta
|
|
float dt = -((mouseX - m_mouseState.m_lastMouseCoords.x) * m_timeline.GetScale());
|
|
CAnimSceneEvent* pEvt = m_selected.GetEvent();
|
|
pEvt->SetPreloadDuration(Clamp(pEvt->GetPreloadDuration()+dt, 0.0f, pEvt->GetStart() - Max(0.0f, m_timeline.GetMinVisibleTime())));
|
|
}
|
|
else
|
|
{
|
|
m_flags.ClearFlag(kDraggingEventPreLoad);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
// left click with nothing highlighted
|
|
if (leftMousePressed && !m_flags.IsFlagSet(kMadeEventSelectionThisClick))
|
|
{
|
|
// deselect the currently selected event
|
|
SelectEvent(NULL);
|
|
}
|
|
}
|
|
|
|
if (!leftMouseDown && leftMouseReleased)
|
|
{
|
|
m_flags.ClearFlag(kMadeEventSelectionThisClick);
|
|
//Ensure that dragging is disabled
|
|
m_flags.ClearFlag(kDraggingEvent | kDraggingEventEnd | kDraggingEventPreLoad | kDraggingEventStart);
|
|
}
|
|
|
|
// keep the scene duration in sync with the events
|
|
if (GetSelectedEvent() && IsDraggingEvent())
|
|
{
|
|
GetSelectedEvent()->NotifyRangeUpdated();
|
|
}
|
|
|
|
if(m_flags.IsFlagSet(kRegenerateEventTypeWidgets))
|
|
{
|
|
if(m_bAllowWidgetAutoRegen)
|
|
{
|
|
RegenEventTypeWidgets();
|
|
}
|
|
m_flags.ClearFlag(kRegenerateEventTypeWidgets);
|
|
}
|
|
|
|
if (m_flags.IsFlagSet(kRegenerateNewEventWidgets))
|
|
{
|
|
bkBank* pBank = CDebugClipSelector::FindBank(m_widgets.m_pAddEventGroup);
|
|
if (pBank)
|
|
{
|
|
AddNewEventWidgetsForEntity(GetSelectedEntity(), m_widgets.m_pAddEventGroup);
|
|
}
|
|
m_flags.ClearFlag(kRegenerateNewEventWidgets);
|
|
}
|
|
|
|
if (m_flags.IsFlagSet(kRegenerateSelectionWidgets))
|
|
{
|
|
// regen the editing widgets
|
|
if (m_widgets.m_pSelectionGroup)
|
|
{
|
|
if (GetScene())
|
|
{
|
|
GetScene()->DoWidgetShutdownCallbacks();
|
|
}
|
|
|
|
m_widgets.m_playbackListLeadInClipSetSelector.RemoveWidgets();
|
|
ClearSelectionWidgets();
|
|
// if an event is selected, show the widgets for that, otherwise, if only an entity is selected, show its widgets
|
|
bkBank* pBank = CDebugClipSelector::FindBank(m_widgets.m_pSelectionGroup);
|
|
if (GetSelectedEvent() && pBank)
|
|
{
|
|
pBank->SetCurrentGroup(*m_widgets.m_pSelectionGroup);
|
|
CAnimScene::SetCurrentAddWidgetsScene(m_pScene);
|
|
|
|
PARSER.AddWidgets(*pBank, GetSelectedEvent());
|
|
|
|
CAnimScene::SetCurrentAddWidgetsScene(NULL);
|
|
pBank->UnSetCurrentGroup(*m_widgets.m_pSelectionGroup);
|
|
}
|
|
else if (GetSelectedEntity() && pBank)
|
|
{
|
|
pBank->SetCurrentGroup(*m_widgets.m_pSelectionGroup);
|
|
CAnimScene::SetCurrentAddWidgetsScene(m_pScene);
|
|
|
|
PARSER.AddWidgets(*pBank, GetSelectedEntity());
|
|
|
|
CAnimScene::SetCurrentAddWidgetsScene(NULL);
|
|
|
|
if (GetSelectedEntity()->GetType()==ANIM_SCENE_ENTITY_PED)
|
|
{
|
|
m_widgets.m_playbackListLeadInClipSetSelector.AddWidgets(pBank, "LeadIn Clipset Selector:", datCallback(MFA(CAnimSceneEditor::LeadInSelected), this));
|
|
}
|
|
|
|
pBank->UnSetCurrentGroup(*m_widgets.m_pSelectionGroup);
|
|
}
|
|
}
|
|
|
|
SyncPickerFromAnimSceneEntity();
|
|
m_flags.SetFlag(kRegenerateEventTypeWidgets);
|
|
m_flags.ClearFlag(kRegenerateSelectionWidgets);
|
|
}
|
|
|
|
|
|
|
|
// handle scene control.
|
|
if (m_pScene)
|
|
{
|
|
if (!m_pScene->IsInitialised())
|
|
{
|
|
// load the scene
|
|
m_pScene->BeginLoad();
|
|
SynchroniseHoldAtEndFlag();
|
|
}
|
|
else if (m_pScene->IsFinished())
|
|
{
|
|
// restart the scene
|
|
if(m_editorSettingLoopPlayback)
|
|
{
|
|
m_pScene->Reset();
|
|
}
|
|
}
|
|
else if (m_pScene->IsLoaded() && !m_pScene->IsPlayingBack())
|
|
{
|
|
if (m_editorSettingAutoRegisterPlayer)
|
|
{
|
|
CPed* pPlayerPed = FindPlayerPed();
|
|
|
|
if (pPlayerPed)
|
|
{
|
|
CAnimScenePed* pScenePed = m_pScene->GetEntity<CAnimScenePed>(pPlayerPed->GetModelName(), ANIM_SCENE_ENTITY_PED);
|
|
if (pScenePed)
|
|
{
|
|
pScenePed->SetPed(pPlayerPed);
|
|
}
|
|
}
|
|
}
|
|
|
|
if (!m_flags.IsFlagSet(kInitialTimelineZoomSet))
|
|
{
|
|
m_timeline.CalculateInitialZoom(0.0f, m_pScene->GetDuration());
|
|
m_flags.SetFlag(kInitialTimelineZoomSet);
|
|
}
|
|
|
|
bool wasPaused = m_pScene->GetPaused();
|
|
|
|
// start the scene
|
|
m_pScene->Start();
|
|
|
|
m_pScene->SetPaused(wasPaused);
|
|
|
|
if (m_editorSettingPauseSceneAtFirstStart && m_firstPlayback)
|
|
{
|
|
m_pScene->SetPaused(true);
|
|
m_firstPlayback = false;
|
|
}
|
|
}
|
|
else if (m_pScene->IsPlayingBack())
|
|
{
|
|
if (!m_timeline.IsDraggingSelector())
|
|
{
|
|
// sync the timeline to the scene progress
|
|
m_timeline.SetCurrentTime(m_pScene->GetTimeWithSkipping());
|
|
|
|
if (!m_pScene->GetPaused())
|
|
{
|
|
// Update visual timeline according to user preference
|
|
if (m_editorSettingTimelinePlaybackMode == kTimelinePlaybackMode_SelectorInCentre)
|
|
{
|
|
m_timeline.MoveMarkerToVisibleTimelinePosition(0.5f);
|
|
}
|
|
else if (m_editorSettingTimelinePlaybackMode == kTimelinePlaybackMode_MaintainSelectorPosition)
|
|
{
|
|
m_timeline.MoveMarkerToVisibleTimelinePosition(m_fSelectorTimelinePositionUponPlayback);
|
|
}
|
|
}
|
|
|
|
// overrides holding at last frame, restart the scene if looping is enabled
|
|
/*
|
|
if(m_editorSettingLoopPlayback)
|
|
{
|
|
if(m_timeline.GetCurrentTime >= m_pScene->GetDuration())
|
|
{
|
|
m_pScene->Reset();
|
|
}
|
|
}*/
|
|
}
|
|
}
|
|
|
|
// handle deleting selected scene elements using the DELETE key.
|
|
// for some reason the delete key checks below sometimes return TRUE
|
|
// for multiple frames in succession, so we ignore subsequent delete commands
|
|
// for a few frames.
|
|
|
|
static u32 s_lastDeleteDelay = 3;
|
|
static u32 s_lastDeleteFrame = 0;
|
|
|
|
if (((fwTimer::GetFrameCount() - s_lastDeleteFrame) > s_lastDeleteDelay) &&
|
|
(CControlMgr::GetKeyboard().GetKeyJustDown(KEY_DELETE, KEYBOARD_MODE_GAME) || CControlMgr::GetKeyboard().GetKeyJustDown(KEY_DELETE, KEYBOARD_MODE_DEBUG) || m_pScene->GetShouldDeleteEntityFromWidgetCB()))
|
|
{
|
|
|
|
if (GetSelectedEvent() && GetFocus()==kFocusEvent)
|
|
{
|
|
char msg[200];
|
|
atString eventText;
|
|
GetSelectedEvent()->GetEditorEventText(eventText,*this);
|
|
formatf(msg,200,"[%s] Are you sure you wish to delete this event? You won't be able to undo this.",eventText.c_str());
|
|
if (bkMessageBox("Confirm delete", msg, bkMsgYesNo, bkMsgQuestion))
|
|
{
|
|
CAnimSceneEvent* pEventToDelete = GetSelectedEvent();
|
|
ClearSelectionWidgets();
|
|
SelectEvent(NULL);
|
|
m_pScene->DeleteEvent(pEventToDelete);
|
|
//recalculate section lengths
|
|
m_pScene->RecalculateSceneDurations();
|
|
}
|
|
}
|
|
else if (GetSelectedEntity() && GetFocus()==kFocusEntity)
|
|
{
|
|
char msg[200];
|
|
atString entityText;
|
|
CAnimSceneEntity::Id entityId = GetSelectedEntity()->GetId();
|
|
formatf(msg,200,"[%s] Are you sure you wish to delete this entity? You won't be able to undo this",entityId.TryGetCStr());
|
|
if (bkMessageBox("Confirm delete", msg, bkMsgYesNo, bkMsgQuestion))
|
|
{
|
|
CAnimSceneEntity* pEntityToDelete = GetSelectedEntity();
|
|
ClearSelectionWidgets();
|
|
SelectEvent(NULL);
|
|
SelectEntity(NULL);
|
|
m_pScene->DeleteAllEventsForEntity(pEntityToDelete->GetId());
|
|
m_pScene->DeleteEntity(pEntityToDelete);
|
|
m_pScene->RecalculateSceneDurations();
|
|
}
|
|
}
|
|
else if (m_sectionPanel.GetSelectedPlaybackList()!=ANIM_SCENE_PLAYBACK_LIST_ID_INVALID && GetFocus()==kFocusPlaybackList)
|
|
{
|
|
char msg[200];
|
|
formatf(msg,200,"[%s] Are you sure you wish to delete this playback list? You won't be able to undo this",m_sectionPanel.GetSelectedPlaybackList().GetCStr());
|
|
if (bkMessageBox("Confirm delete", msg, bkMsgYesNo, bkMsgQuestion))
|
|
{
|
|
m_pScene->DeletePlaybackList(m_sectionPanel.GetSelectedPlaybackList());
|
|
m_sectionPanel.SetSelectedPlaybackList(ANIM_SCENE_PLAYBACK_LIST_ID_INVALID);
|
|
}
|
|
}
|
|
else if (m_sectionPanel.GetSelectedSection()!=ANIM_SCENE_SECTION_ID_INVALID && GetFocus()==kFocusSection)
|
|
{
|
|
char msg[200];
|
|
formatf(msg,200,"[%s] Are you sure you wish to delete this section? You won't be able to undo this",m_sectionPanel.GetSelectedSection().GetCStr());
|
|
if (bkMessageBox("Confirm delete", msg, bkMsgYesNo, bkMsgQuestion))
|
|
{
|
|
m_pScene->DeleteSection(m_sectionPanel.GetSelectedSection());
|
|
m_sectionPanel.SetSelectedSection(ANIM_SCENE_SECTION_ID_INVALID);
|
|
}
|
|
}
|
|
|
|
m_pScene->SetShouldDeleteEntityFromWidgetCB(false);
|
|
s_lastDeleteFrame = fwTimer::GetFrameCount();
|
|
}
|
|
|
|
// deselect the selected entity when clicking on the map, etc
|
|
if (ioMouse::GetPressedButtons() & ioMouse::MOUSE_LEFT && !IsDragging() && !m_flags.IsFlagSet(kMadeEntitySelectionThisFrame) && !IsSelectingADifferentGameEntity())
|
|
{
|
|
SelectEntity(NULL);
|
|
}
|
|
|
|
if (ioMouse::GetReleasedButtons() & ioMouse::MOUSE_LEFT)
|
|
{
|
|
m_pSelectedEventOnLastRelease = m_selected.GetEvent();
|
|
}
|
|
}
|
|
|
|
//---- Handle display of scrollbar if there are too many tracks displayed on screen
|
|
//Compute sum of events (timelines) Y size
|
|
float totalYSize = 0.f;
|
|
atArray<CEventLayerPanel*>& eventLayers = m_EventLayersWindow.GetEventLayers();
|
|
for(int i= 0; i < eventLayers.GetCount(); i++)
|
|
{
|
|
if(eventLayers[i])
|
|
{
|
|
totalYSize += eventLayers[i]->GetTotalPanelHeight();
|
|
}
|
|
}
|
|
//proportion of events on screen as compared to the whole number of events
|
|
float screenEventsProportion = (m_EventLayersWindow.GetScreenExtents().GetMaxY() - m_EventLayersWindow.GetScreenExtents().GetMinY()) / totalYSize;
|
|
if(screenEventsProportion < 1.f)
|
|
{
|
|
m_eventsScrollbar.SetBarHidden(false);
|
|
m_eventsScrollbar.SetBarSize(screenEventsProportion);
|
|
m_eventsScrollbar.SetMinValue(0.f);
|
|
m_eventsScrollbar.SetMaxValue(totalYSize);
|
|
m_eventsScrollbar.SetValue(-m_EventLayersYScreenOffset);
|
|
if(m_eventsScrollbar.IsDragging() || !IsDragging())
|
|
{
|
|
m_eventsScrollbar.ProcessMouseInput();
|
|
}
|
|
m_EventLayersYScreenOffset = -m_eventsScrollbar.GetValue();
|
|
}
|
|
else
|
|
{
|
|
m_eventsScrollbar.SetBarHidden(true);
|
|
m_eventsScrollbar.SetMaxValue(totalYSize);
|
|
m_eventsScrollbar.SetMinValue(0.f);
|
|
m_EventLayersYScreenOffset = 0.f;
|
|
}
|
|
|
|
RenderSelectedAnimScenesPossibleNewGameEntity();
|
|
}
|
|
|
|
bool CAnimSceneEditor::GetDisplayMiniMapThisUpdate()
|
|
{
|
|
return !IsActive();
|
|
}
|
|
|
|
void CAnimSceneEditor::TimelineSelectorDragged(float fNewTime)
|
|
{
|
|
// if dragging the time control, skip the scene to the selected time on the timeline, and pause the scene
|
|
if (m_pScene && m_pScene->IsPlayingBack())
|
|
{
|
|
m_pScene->Skip(fNewTime);
|
|
m_pScene->SetPaused(true);
|
|
}
|
|
}
|
|
|
|
// PURPOSE: Set the screen extents of the editor
|
|
void CAnimSceneEditor::SetScreenExtents(const CScreenExtents& screenExtents)
|
|
{
|
|
TUNE_FLOAT(testWidth, 200.0f, 0.0f, 2000.0f, 1.0f)
|
|
TUNE_FLOAT(testHeight, 22.0f, 0.0f, 2000.0f, 1.0f)
|
|
m_screenExtents = screenExtents;
|
|
|
|
static float s_textPadding = 12.0f;
|
|
static float s_entityPaneWidth = 200.0f;
|
|
static float s_timelineControlHeightOffset = 2.0f;
|
|
static float s_sceneControlHeight = 40.0f;
|
|
static float s_timelineSceneControlGap = 10.0f;
|
|
static float s_windowGaps = 5.0f;
|
|
static float s_videoPanelWidth = 140.0f;
|
|
static float s_videoPanelHeight = 22.0f;
|
|
const float timelineMinX = m_screenExtents.GetMinX() + s_entityPaneWidth;
|
|
const float timelineMaxX = m_screenExtents.GetMaxX();
|
|
|
|
float textBoxHeight = GetTextHeight() + 2.0f*s_textPadding;
|
|
float sceneControlHeight = Max(s_sceneControlHeight, textBoxHeight);
|
|
float timelineControlHeight = textBoxHeight + s_timelineControlHeightOffset;
|
|
|
|
// section panel at the top
|
|
m_sectionPanel.SetScreenExtents(CScreenExtents(m_screenExtents.GetMinX(), screenExtents.GetMinY() + textBoxHeight, screenExtents.GetMaxX(),screenExtents.GetMinY()+(textBoxHeight*3.0f)));
|
|
|
|
// Scene control widgets at bottom of screen, below the timeline
|
|
m_videoPlayBackControl.SetScreenExtents(CScreenExtents(timelineMinX, screenExtents.GetMaxY() - sceneControlHeight, timelineMinX +s_videoPanelWidth, screenExtents.GetMaxY() - sceneControlHeight + s_videoPanelHeight));
|
|
|
|
// Translation & Rotation Helper buttons
|
|
m_authoringDisplay.SetScreenExtents(CScreenExtents(m_videoPlayBackControl.GetScreenExtents().GetMaxX() + s_windowGaps, screenExtents.GetMaxY() - sceneControlHeight, m_videoPlayBackControl.GetScreenExtents().GetMaxX() + s_windowGaps + testWidth, screenExtents.GetMaxY() - sceneControlHeight+ testHeight));
|
|
|
|
// Timeline at the bottom of the screen, above the scene control widgets
|
|
m_timeline.SetScreenExtents(CScreenExtents(timelineMinX, m_videoPlayBackControl.GetScreenExtents().GetMinY() - timelineControlHeight - s_timelineSceneControlGap, timelineMaxX, m_videoPlayBackControl.GetScreenExtents().GetMinY() - s_timelineSceneControlGap));
|
|
|
|
// Scene display next to the timeline
|
|
m_sceneInfoDisplay.SetScreenExtents(CScreenExtents(m_screenExtents.GetMinX(), m_videoPlayBackControl.GetScreenExtents().GetMinY() - timelineControlHeight - s_timelineSceneControlGap, timelineMinX - 5.0f, m_timeline.GetScreenExtents().GetMinY() + (GetTextHeight()*2.0f) + 6.0f));
|
|
m_sceneInfoDisplay.SetTextColour(GetColor(kMainTextColor));
|
|
|
|
// Left column for the entity pane
|
|
m_EventLayersWindow.SetScreenExtents(CScreenExtents(m_screenExtents.GetMinX(), m_sectionPanel.GetScreenExtents().GetMaxY() + s_videoPanelHeight, timelineMinX, m_timeline.GetScreenExtents().GetMinY()));
|
|
|
|
|
|
}
|
|
|
|
// PURPOSE: Set the anim scene currently being edited
|
|
void CAnimSceneEditor::SetAnimScene(CAnimScene* pScene)
|
|
{
|
|
m_pScene = pScene;
|
|
}
|
|
|
|
void CAnimSceneEditor::ComputeEventLayerInfo(CAnimSceneEvent* evt)
|
|
{
|
|
animAssert(evt);
|
|
|
|
TUNE_FLOAT(eventRenderFix, 0.0f, -1000.0f, 1000.0f, 1.0f)
|
|
|
|
atHashString eventLayer(evt->GetPrimaryEntityId());
|
|
atString eventSubGroupText(evt->parser_GetStructure()->GetName());
|
|
eventSubGroupText.Replace("CAnimScene", "");
|
|
eventSubGroupText.Replace("Event","");
|
|
atHashString eventSubGroup(eventSubGroupText.c_str());
|
|
|
|
//float yOffset = m_screenExtents.GetMinY() + EventLayer::ms_layerHeight;
|
|
u32 position = 0;
|
|
// first check if we've already encountered this layer, and add
|
|
// a new one if not:
|
|
for (s32 i=0 ; i<m_EventLayersWindow.GetEventLayers().GetCount(); i++)
|
|
{
|
|
//layer is an entitys group
|
|
CEventLayerPanel& layer = *m_EventLayersWindow.GetEventLayers()[i];
|
|
if (layer.GetName().GetHash()==eventLayer.GetHash())
|
|
{
|
|
// found the layer, now check the sub group
|
|
for (s32 j=0; j<layer.GetEventGroup().GetCount(); j++)
|
|
{
|
|
if (layer.GetEventGroup()[j]->GetName().GetHash()==eventSubGroup.GetHash())
|
|
{
|
|
// check if we overlap with any other events in the group
|
|
//layer.m_subGroups[i].m_events.PushAndGrow(evt);
|
|
|
|
EventInfo Info;
|
|
Info.event = evt;
|
|
Info.position = position;
|
|
layer.GetEventGroup()[j]->AddEvent(Info);
|
|
return;
|
|
}
|
|
//yOffset+=EventLayer::ms_layerHeight;
|
|
position++;
|
|
}
|
|
|
|
layer.AddEventGroup(eventSubGroup);
|
|
|
|
for (s32 j=0; j<layer.GetEventGroup().GetCount(); j++)
|
|
{
|
|
if (layer.GetEventGroup()[j]->GetName().GetHash()==eventSubGroup.GetHash())
|
|
{
|
|
// check if we overlap with any other events in the group
|
|
//layer.m_subGroups[i].m_events.PushAndGrow(evt);
|
|
|
|
EventInfo Info;
|
|
Info.event = evt;
|
|
Info.position = position;
|
|
layer.GetEventGroup()[j]->AddEvent(Info);
|
|
return;
|
|
}
|
|
//yOffset+=EventLayer::ms_layerHeight;
|
|
position++;
|
|
}
|
|
return;
|
|
//return yOffset;
|
|
}
|
|
else
|
|
{
|
|
//yOffset += Max(layer.m_subGroups.GetCount(), 1)*EventLayer::ms_layerHeight;
|
|
}
|
|
}
|
|
|
|
m_EventLayersWindow.AddEventLayerPanel(eventLayer);
|
|
//return yOffset;
|
|
}
|
|
|
|
void CAnimSceneEditor::UpdateEventLayerInfo(CAnimSceneEvent* evt)
|
|
{
|
|
if (evt)
|
|
{
|
|
ComputeEventLayerInfo(evt);
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void CAnimSceneEditor::AddWidgets(bkGroup* pParentGroup)
|
|
{
|
|
Assert(pParentGroup);
|
|
|
|
sprintf(m_widgets.m_saveStatusTextArray, "");
|
|
|
|
m_widgets.m_pSaveButton = pParentGroup->AddButton("Save scene", datCallback(MFA(CAnimSceneEditor::SaveCurrentScene), this));
|
|
m_widgets.m_pSaveStatus = pParentGroup->AddText("", m_widgets.m_saveStatusTextArray, 31, true);
|
|
m_widgets.m_pCloseButton = pParentGroup->AddButton("Close scene", datCallback(MFA(CAnimSceneEditor::TriggerCloseCurrentScene), this) );
|
|
|
|
m_widgets.m_pSceneGroup = pParentGroup->AddGroup("Scene details");
|
|
bkBank* pBank = CDebugClipSelector::FindBank(m_widgets.m_pSceneGroup);
|
|
pBank->SetCurrentGroup(*m_widgets.m_pSceneGroup);
|
|
PARSER.AddWidgets(*pBank, m_pScene);
|
|
pBank->UnSetCurrentGroup(*m_widgets.m_pSceneGroup);
|
|
|
|
m_widgets.m_pAddEntityGroup = pParentGroup->AddGroup("Add Entity");
|
|
|
|
// create the selection list for entities
|
|
{
|
|
m_widgets.m_pAddEntityGroup->AddText("Entity Id", &m_widgets.m_newEntityId);
|
|
|
|
m_widgets.m_entityNameList.clear();
|
|
m_widgets.m_entityNameList.PushAndGrow("Select an entity to add");
|
|
|
|
for (s32 i=0 ;i<m_entityInitialisers.GetCount(); i++)
|
|
{
|
|
if (m_entityInitialisers[i])
|
|
{
|
|
m_widgets.m_entityNameList.PushAndGrow(m_entityInitialisers[i]->GetFriendlyEntityTypeName().GetCStr());
|
|
}
|
|
}
|
|
|
|
if(m_entityInitialisers.GetCount() > 3)
|
|
{
|
|
m_widgets.m_selectedEntityType = 3; // Is probably Ped, but really this should be done properly.
|
|
}
|
|
m_widgets.m_pEntityTypeCombo = m_widgets.m_pAddEntityGroup->AddCombo("Entity type", (unsigned char *)(&(m_widgets.m_selectedEntityType)), m_widgets.m_entityNameList.GetCount(), &(m_widgets.m_entityNameList[0]), datCallback(MFA(CAnimSceneEditor::RegenEntityTypeWidgets), this), 0, NULL);
|
|
RegenEntityTypeWidgets();
|
|
}
|
|
|
|
m_widgets.m_pAddSectionGroup = pParentGroup->AddGroup("Sectioning");
|
|
{
|
|
m_widgets.m_pAddSectionGroup->AddText("New section / playback list name", &m_widgets.m_newSectionId);
|
|
m_widgets.m_pAddSectionGroup->AddButton("Add new section", datCallback(MFA(CAnimSceneEditor::AddNewSection), this));
|
|
m_widgets.m_pAddSectionGroup->AddButton("Delete this section", datCallback(MFA(CAnimSceneEditor::DeleteSection), this));
|
|
m_widgets.m_pAddSectionGroup->AddButton("Add new playback list", datCallback(MFA(CAnimSceneEditor::AddNewPlaybackList), this));
|
|
}
|
|
|
|
m_widgets.m_pAddEventGroup = pParentGroup->AddGroup("Add Event");
|
|
{
|
|
|
|
}
|
|
|
|
m_widgets.m_pSelectionGroup = pParentGroup->AddGroup("Current selection");
|
|
}
|
|
|
|
void CAnimSceneEditor::AddEditorWidgets(bkGroup* pParentGroup)
|
|
{
|
|
Assert(pParentGroup);
|
|
|
|
bkGroup* pGeneralGroup = pParentGroup->AddGroup("General");
|
|
{
|
|
pGeneralGroup->AddToggle("Use Smooth Font", &m_editorSettingUseSmoothFont, datCallback(MFA(CAnimSceneEditor::RefreshScreenExtents), this));
|
|
pGeneralGroup->AddToggle("Hide events tracks", &m_editorSettingHideEvents);
|
|
pGeneralGroup->AddToggle("Hold at last frame", &m_editorSettingHoldAtLastFrame, datCallback(MFA(CAnimSceneEditor::SynchroniseHoldAtEndFlag), this));
|
|
pGeneralGroup->AddToggle("Loop playback in editor (only if not holding)", &m_editorSettingLoopPlayback, datCallback(MFA(CAnimSceneEditor::LoopEditorToggleCB), this));
|
|
pGeneralGroup->AddToggle("Pause scene after first load", &m_editorSettingPauseSceneAtFirstStart);
|
|
pGeneralGroup->AddToggle("Reset scene on playback list change", &m_editorSettingResetSceneOnPlaybackListChange);
|
|
pGeneralGroup->AddToggle("Auto register player (using model name)", &m_editorSettingAutoRegisterPlayer);
|
|
pGeneralGroup->AddToggle("Use event colour for marker rendering.", &ms_editorSettingUseEventColourForMarker);
|
|
pGeneralGroup->AddToggle("Regen widgets automatically when new event is selected (for repeated play anim adding).", &m_bAllowWidgetAutoRegen);
|
|
pGeneralGroup->AddSlider("Background alpha.", &ms_editorSettingBackgroundAlpha,0.0f,1.0f,0.05f);
|
|
pGeneralGroup->AddButton("Validate Scene", datCallback(MFA(CAnimSceneEditor::ValidateScene), (datBase*)this));
|
|
}
|
|
|
|
bkGroup* pTimelineGroup = pParentGroup->AddGroup("Timeline");
|
|
{
|
|
static const char* playbackModes[kTimelinePlaybackMode_Num] = {"Maintain Selector Position", "Keep Selector In Centre", "Do not move timeline"};
|
|
pTimelineGroup->AddCombo("Playback Behaviour", &m_editorSettingTimelinePlaybackMode, kTimelinePlaybackMode_Num, playbackModes);
|
|
|
|
static const char* timelineDisplayMode[kTimelineDisplayMode_Num] = {"Frames", "Seconds"};
|
|
pTimelineGroup->AddCombo("Time Display Mode", &m_editorSettingTimelineDisplayMode, kTimelineDisplayMode_Num, timelineDisplayMode, datCallback(MFA(CAnimSceneEditor::TimelineDisplayModeChangedCB), (datBase*)this) );
|
|
|
|
pTimelineGroup->AddToggle("Snap To Frames", &m_editorSettingTimelineSnapToFrames, datCallback(MFA(CAnimSceneEditor::TimelineSnapChangedCB), (datBase*)this));
|
|
}
|
|
|
|
bkGroup* pEditorGroup = pParentGroup->AddGroup("Event Editing");
|
|
{
|
|
pEditorGroup->AddToggle("Edit event preload times", &m_editorSettingEditEventPreloads);
|
|
pEditorGroup->AddToggle("Clamp anim event lengths to anim lengths", &CAnimScenePlayAnimEvent::ms_editorSettings.m_clampEventLengthToAnim);
|
|
pEditorGroup->AddToggle("Display anim event dictionaries (when hovering)", &CAnimScenePlayAnimEvent::ms_editorSettings.m_displayDictionaryNames);
|
|
pEditorGroup->AddToggle("Snap To Frames When Editing Events", &m_editorSettingEventEditorSnapToFrames);
|
|
pEditorGroup->AddSlider("Events Scrolling", &m_EventLayersYScreenOffset, -1000.0f, 500.0f, 1.0f);
|
|
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::SelectEntity(CAnimSceneEntity* pEntity, bool setFocus /*= true*/)
|
|
{
|
|
if (pEntity!= m_selected.GetEntity())
|
|
{
|
|
m_flags.SetFlag(kRegenerateSelectionWidgets | kRegenerateNewEventWidgets);
|
|
}
|
|
|
|
m_selected.SelectEntity(pEntity);
|
|
|
|
if (pEntity && setFocus)
|
|
{
|
|
SetFocus(kFocusEntity);
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::SelectEvent(CAnimSceneEvent* pEvent, bool setFocus /*= true*/)
|
|
{
|
|
if (pEvent!= m_selected.GetEvent())
|
|
{
|
|
m_flags.SetFlag(kRegenerateSelectionWidgets);
|
|
|
|
CAnimSceneEntity::Id eventEntId = pEvent ? pEvent->GetPrimaryEntityId() : ANIM_SCENE_ENTITY_ID_INVALID;
|
|
CAnimSceneEntity::Id selectedEntId = GetSelectedEntity() ? GetSelectedEntity()->GetId() : ANIM_SCENE_ENTITY_ID_INVALID;
|
|
|
|
if (eventEntId.GetHash()!=selectedEntId.GetHash())
|
|
{
|
|
// GetEntity returns null if the id is invalid
|
|
SelectEntity(m_pScene->GetEntity(eventEntId));
|
|
m_flags.SetFlag(kMadeEventSelectionThisClick);
|
|
}
|
|
else if (pEvent==NULL)
|
|
{
|
|
m_pSelectedEventOnLastRelease = NULL;
|
|
}
|
|
}
|
|
|
|
m_selected.SelectEvent(pEvent);
|
|
if (pEvent && setFocus)
|
|
{
|
|
SetFocus(kFocusEvent);
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::SaveCurrentScene()
|
|
{
|
|
sprintf(m_widgets.m_saveStatusTextArray, "");
|
|
if (m_pScene)
|
|
{
|
|
bool bResult = m_pScene->Save();
|
|
|
|
sprintf(m_widgets.m_saveStatusTextArray, "Save %s", bResult ? "Successful" : "Failed");
|
|
|
|
CAnimSceneManager::LoadSceneNameList();
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::TriggerCloseCurrentScene()
|
|
{
|
|
m_flags.SetFlag(kCloseCurrentScene);
|
|
}
|
|
|
|
Color32 CAnimSceneEditor::GetColor(eColorType type)
|
|
{
|
|
if(type < kMaxNumColors)
|
|
{
|
|
return m_colors[type];
|
|
}
|
|
|
|
return Color32(0,0,0,0);
|
|
}
|
|
|
|
void CAnimSceneEditor::SetColor(u32 type, Color32 color)
|
|
{
|
|
if(type < kMaxNumColors)
|
|
{
|
|
m_colors[type] = color;
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::SetAnimSceneEditorColors()
|
|
{
|
|
SetColor(kMainTextColor, ASE_Editor_DefaultTextColor);
|
|
SetColor(kSelectedTextColor, ASE_Editor_SelectedTextColor);
|
|
SetColor(kSelectedTextOutlineColor, ASE_Editor_SelectedTextOutlineColor);
|
|
SetColor(kFocusTextOutlineColor, ASE_Editor_FocusTextOutlineColor);
|
|
SetColor(kTextHoverColor, ASE_Editor_HoveredTextColor);
|
|
SetColor(kTextWarningColor, ASE_Editor_WarningTextColor);
|
|
SetColor(kSelectedTextHoverColor, ASE_Editor_SelectedHoveredTextColor);
|
|
|
|
SetColor(kTextBackgroundColor, ASE_Editor_DefaultTextBackgroundColor);
|
|
SetColor(kSelectedTextBackGroundColor, ASE_Editor_SelectedTextBackgroundColor);
|
|
SetColor(kTextOutlineColor, ASE_Editor_DefaultTextOutlineColor);
|
|
SetColor(kRegionOutlineColor, ASE_Panel_OutlineColor);
|
|
|
|
SetColor(kDisabledTextColor, ASE_Editor_DisabledTextColor);
|
|
SetColor(kDisabledBackgroundColor, ASE_Editor_DisabledBackgroundColor);
|
|
SetColor(kDisabledOutlineColor, ASE_Editor_DisabledOutlineColor);
|
|
|
|
SetColor(kDefaultEventColor, ASE_Panel_EventNorthernBlackColor);
|
|
SetColor(kEventMarkerColor, ASE_Panel_EventMarkerColor);
|
|
SetColor(kEventOutlineColor, ASE_Panel_EventOutlineColor);
|
|
SetColor(kEventBackgroundColor, ASE_Panel_EventBackgroundColor);
|
|
|
|
SetColor(kSelectedEventColor, ASE_Panel_SelectedEventColor);
|
|
SetColor(kSelectedEventMarkerColor, ASE_Panel_SelectedEventMarkerColor);
|
|
SetColor(kSelectedEventOutlineColor, ASE_Panel_SelectedEventOutlineColor);
|
|
SetColor(kSelectedEventDraggingColor, ASE_Panel_SelectedEventDraggingColor);
|
|
|
|
SetColor(kVfxEventColor, ASE_Panel_EventJubileeGreyColor);
|
|
|
|
SetColor(kPlayAnimEventColor, ASE_Panel_EventVictoriaBlueColor);
|
|
SetColor(kPlayAnimEventColorAlt, ASE_Panel_EventDistrictGreen ); //ASE_Panel_EventDistrictGreen, or ASE_Panel_EventNorthernBlackColor
|
|
|
|
SetColor(kEventPreloadLineColor, ASE_Panel_EventPreloadlineColor);
|
|
SetColor(kEventCurrentTimeLineColor, ASE_Panel_EventCurrentTimeLineColor);
|
|
|
|
SetColor(kBlendInMarkerColor, ASE_Panel_EventOGOrangeColor);
|
|
SetColor(kBlendOutMarkerColor, ASE_Panel_EventWCGreenColor);
|
|
|
|
SetColor(kScrollBarBackgroundColour, ASE_Panel_Button_BackGroundColor);
|
|
SetColor(kScrollBarActiveBackgroundColour, ASE_Panel_Button_ActiveBackgroundColor);
|
|
SetColor(kScrollBarHoverBackgroundColour, ASE_Panel_Button_HoverBackgroundColor);
|
|
|
|
SetColor(kSectionDividerColor, ASE_Panel_EventNorthernBlackColor);
|
|
}
|
|
|
|
|
|
bool CAnimSceneEditor::IsDraggingMatrixHelper()
|
|
{
|
|
for(int i=0; i < CAnimSceneMatrix::m_AnimSceneMatrix.GetCount(); i++)
|
|
{
|
|
CAnimSceneMatrix* pAnimSceneMatrix = CAnimSceneMatrix::m_AnimSceneMatrix[i];
|
|
if (pAnimSceneMatrix && pAnimSceneMatrix->GetAuthoringHelper().GetCurrentInput())
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
atHashString CAnimSceneEditor::GetSelectedEntityId()
|
|
{
|
|
return GetSelectedEntity() ? GetSelectedEntity()->GetId() : ANIM_SCENE_ENTITY_ID_INVALID;
|
|
}
|
|
|
|
void CAnimSceneEditor::CloseCurrentScene()
|
|
{
|
|
Shutdown();
|
|
}
|
|
|
|
void CAnimSceneEditor::RegenEntityTypeWidgets()
|
|
{
|
|
CleanupEntityInitialiserWidgets();
|
|
|
|
// clear out any previous widgets:
|
|
while (m_widgets.m_pEntityTypeCombo->GetNext())
|
|
{
|
|
m_widgets.m_pEntityTypeCombo->GetNext()->Destroy();
|
|
}
|
|
|
|
s32 selectedType = m_widgets.m_selectedEntityType;
|
|
|
|
if (selectedType>0 && selectedType < m_widgets.m_entityNameList.GetCount())
|
|
{
|
|
atHashString type(m_widgets.m_entityNameList[selectedType]);
|
|
|
|
bkBank* pBank = CDebugClipSelector::FindBank(m_widgets.m_pAddEntityGroup);
|
|
pBank->SetCurrentGroup(*(m_widgets.m_pAddEntityGroup));
|
|
|
|
CAnimSceneEntityInitialiser* pInit = GetEntityInitialiserFromFriendlyName(type);
|
|
|
|
pInit->AddWidgets(m_widgets.m_pAddEntityGroup, this);
|
|
pInit->m_bRequiresWidgetCleanup = true;
|
|
|
|
m_widgets.m_pAddEntityGroup->AddButton("Add entity", datCallback(MFA(CAnimSceneEditor::AddNewEntity), this));
|
|
|
|
pBank->UnSetCurrentGroup(*(m_widgets.m_pAddEntityGroup));
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::RegenEventTypeWidgets()
|
|
{
|
|
CleanupEventInitialiserWidgets();
|
|
|
|
// clear out any previous widgets:
|
|
while (m_widgets.m_pEventTypeCombo->GetNext())
|
|
{
|
|
m_widgets.m_pEventTypeCombo->GetNext()->Destroy();
|
|
}
|
|
|
|
s32 selectedType = m_widgets.m_selectedEventType;
|
|
if (selectedType>0 && selectedType < m_widgets.m_eventNameList.GetCount())
|
|
{
|
|
atHashString type(m_widgets.m_eventNameList[selectedType]);
|
|
|
|
bkBank* pBank = CDebugClipSelector::FindBank(m_widgets.m_pAddEventGroup);
|
|
bkGroup& group = *(m_widgets.m_pAddEventGroup);
|
|
|
|
pBank->SetCurrentGroup(group);
|
|
|
|
CAnimSceneEventInitialiser* pInitialiser = GetEventInitialiserFromFriendlyName(type);
|
|
|
|
pInitialiser->AddWidgets(&group, this);
|
|
pInitialiser->m_bRequiresWidgetCleanup = true;
|
|
|
|
group.AddButton("Add event", datCallback(MFA(CAnimSceneEditor::AddNewEvent), this));
|
|
|
|
pBank->UnSetCurrentGroup(group);
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::ClearSelectionWidgets()
|
|
{
|
|
if (m_widgets.m_pSelectionGroup)
|
|
{
|
|
m_widgets.m_playbackListLeadInClipSetSelector.RemoveWidgets();
|
|
|
|
while (m_widgets.m_pSelectionGroup->GetChild())
|
|
{
|
|
m_widgets.m_pSelectionGroup->GetChild()->Destroy();
|
|
}
|
|
}
|
|
}
|
|
|
|
CAnimSceneEntity* CAnimSceneEditor::CreateEntityAndAddToSceneEditor(CAnimSceneEntity::Id newID, CAnimSceneEntityInitialiser* pInitialiser, parStructure* pStruct)
|
|
{
|
|
if (animVerifyf(!m_pScene->GetEntity(newID), "An entity with id '%s' already exists in the scene!", newID.GetCStr()))
|
|
{
|
|
CAnimSceneEntity* pNewEnt = (CAnimSceneEntity*)pStruct->Create();
|
|
pNewEnt->SetId(newID);
|
|
pNewEnt->InitForEditor(pInitialiser);
|
|
|
|
// Don't add again if the entity was already added in InitForEditor above
|
|
if (!m_pScene->GetEntity(newID))
|
|
{
|
|
m_pScene->SceneEditorAddEntity(newID, pNewEnt);
|
|
}
|
|
|
|
return pNewEnt;
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
void CAnimSceneEditor::AddNewEntity()
|
|
{
|
|
s32 selectedType = m_widgets.m_selectedEntityType;
|
|
if (selectedType>=0 && selectedType < m_widgets.m_entityNameList.GetCount())
|
|
{
|
|
const char * pType = m_widgets.m_entityNameList[selectedType];
|
|
|
|
CAnimSceneEntity::Id newID(m_widgets.m_newEntityId);
|
|
|
|
if (newID==ANIM_SCENE_ID_INVALID)
|
|
{
|
|
bkMessageBox("Enter an entity Id", "You must enter a valid entity id (empty).", bkMsgOk, bkMsgInfo);
|
|
return;
|
|
}
|
|
|
|
if( !CAnimSceneEntity::IsValidId(newID) )
|
|
{
|
|
animDisplayf("[Anim Scene Editor] Attempting to fix entered entity id: \"%s\"", newID.TryGetCStr());
|
|
if(!FixInvalidId(newID)) //returns true if able to fix
|
|
{
|
|
bkMessageBox("Entered Entity Id", "Unable to automatically fix entity id (empty or contains invalid characters).", bkMsgOk, bkMsgInfo);
|
|
return;
|
|
}
|
|
else
|
|
{
|
|
animDisplayf("[Anim Scene Editor] Successfully fixed to: \"%s\"", newID.TryGetCStr());
|
|
}
|
|
}
|
|
|
|
if (m_pScene->GetEntity(newID))
|
|
{
|
|
bkMessageBox("Entity Id must be unique", "An entity with this Id already exists. Please enter a unique name.", bkMsgOk, bkMsgInfo);
|
|
return;
|
|
}
|
|
|
|
CAnimSceneEntityInitialiser* pInit = GetEntityInitialiserFromFriendlyName(pType);
|
|
|
|
if(!pInit)
|
|
{
|
|
bkMessageBox("Invalid anim scene entity initialiser", "Error adding a new entity! The entity initialiser couldn't be created from the name of the type.", bkMsgOk, bkMsgError);
|
|
return;
|
|
}
|
|
|
|
parStructure* pStruct = PARSER.FindStructure(pInit->GetEntityTypeName().GetCStr());
|
|
|
|
if(!pStruct)
|
|
{
|
|
bkMessageBox("Invalid entity type", "Error adding a new entity! The selected entity type is not recognised", bkMsgOk, bkMsgError);
|
|
return;
|
|
}
|
|
|
|
atHashString type(pType);
|
|
|
|
CreateEntityAndAddToSceneEditor(newID, pInit, pStruct);
|
|
}
|
|
}
|
|
|
|
CAnimSceneEvent* CAnimSceneEditor::CreateEventAndAddToCurrentScene(const char * eventTypeName, CAnimSceneEventInitialiser* pInitialiser, atHashString sectionId)
|
|
{
|
|
CAnimSceneEvent* pNewEvent = CreateNewEventOfType(eventTypeName);
|
|
|
|
pInitialiser->m_pEditor = this;
|
|
pInitialiser->m_pSection = m_pScene->GetSection(sectionId);
|
|
|
|
pNewEvent->SetParentList(&m_pScene->GetSection(sectionId)->GetEvents());
|
|
|
|
if(!pNewEvent->InitForEditor(pInitialiser))
|
|
{
|
|
delete pNewEvent;
|
|
return NULL;
|
|
}
|
|
|
|
m_pScene->SceneEditorAddEvent(pNewEvent, sectionId);
|
|
|
|
return pNewEvent;
|
|
}
|
|
|
|
CAnimSceneEvent* CAnimSceneEditor::CreateNewEventOfType(const char * typeName)
|
|
{
|
|
parStructure* pStruct = PARSER.FindStructure(typeName);
|
|
|
|
if(!pStruct)
|
|
{
|
|
bkMessageBox("Invalid event type", "Error creating a new event! The selected event type is not recognised", bkMsgOk, bkMsgError);
|
|
return NULL;
|
|
}
|
|
|
|
return (CAnimSceneEvent*)pStruct->Create();
|
|
}
|
|
|
|
void CAnimSceneEditor::AddNewEvent()
|
|
{
|
|
s32 selectedType = m_widgets.m_selectedEventType;
|
|
if (selectedType>=0 && selectedType < m_widgets.m_eventNameList.GetCount())
|
|
{
|
|
CAnimSceneEventInitialiser* pInitialiser = GetEventInitialiserFromFriendlyName(atHashString(m_widgets.m_eventNameList[selectedType]));
|
|
pInitialiser->m_pEntity = GetSelectedEntity();
|
|
animAssertf(pInitialiser->m_pEntity,"When adding new event, couldn't get selected entity.");
|
|
|
|
const char * pType = pInitialiser->GetEventTypeName().GetCStr();
|
|
|
|
CAnimSceneSection::Id sectionId;
|
|
|
|
if (!m_widgets.m_addEventSectionSelector.HasSelection() || m_widgets.m_addEventSectionSelector.GetSelectedIndex()==0)
|
|
{
|
|
sectionId = m_pScene->FindSectionForTime(GetCurrentTime());
|
|
}
|
|
else
|
|
{
|
|
sectionId.SetFromString(m_widgets.m_addEventSectionSelector.GetSelectedName());
|
|
}
|
|
|
|
CreateEventAndAddToCurrentScene(pType, pInitialiser, sectionId);
|
|
}
|
|
}
|
|
|
|
//This needs to refresh the section on the add event section in RAG (if it exists)
|
|
void CAnimSceneEditor::AddNewSection()
|
|
{
|
|
m_pScene->AddNewSection(m_widgets.m_newSectionId);
|
|
}
|
|
|
|
void CAnimSceneEditor::AddNewPlaybackList()
|
|
{
|
|
m_pScene->AddNewPlaybackList(m_widgets.m_newSectionId);
|
|
}
|
|
|
|
void CAnimSceneEditor::LeadInSelected()
|
|
{
|
|
CAnimSceneEntity* pEnt = GetSelectedEntity();
|
|
if (m_pScene && pEnt && pEnt->GetType()==ANIM_SCENE_ENTITY_PED)
|
|
{
|
|
CAnimScenePed* pPedEnt = static_cast<CAnimScenePed*>(pEnt);
|
|
fwMvClipSetId clipSet(CLIP_SET_ID_INVALID);
|
|
if (m_widgets.m_playbackListLeadInClipSetSelector.HasSelection())
|
|
{
|
|
clipSet.SetFromString(m_widgets.m_playbackListLeadInClipSetSelector.GetSelectedName());
|
|
}
|
|
|
|
pPedEnt->SetLeadInClipSet(m_sectionPanel.GetSelectedPlaybackList(), clipSet);
|
|
}
|
|
|
|
}
|
|
|
|
void CAnimSceneEditor::DeleteSection()
|
|
{
|
|
if (bkMessageBox("Confirm delete", "Are you sure you wish to delete this section? You won't be able to undo this.", bkMsgYesNo, bkMsgQuestion))
|
|
{
|
|
m_pScene->DeleteSection(m_widgets.m_newSectionId);
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::AddNewEventWidgetsForEntity(CAnimSceneEntity* pEntity, bkGroup* pGroup)
|
|
{
|
|
// clear the group contents
|
|
CleanupEventInitialiserWidgets();
|
|
|
|
m_widgets.m_addEventSectionSelector.RemoveWidgets();
|
|
|
|
while (pGroup->GetChild())
|
|
{
|
|
pGroup->GetChild()->Destroy();
|
|
}
|
|
|
|
bkBank* pBank = CDebugClipSelector::FindBank(pGroup);
|
|
|
|
pBank->SetCurrentGroup(*pGroup);
|
|
m_widgets.m_addEventSectionSelector.SetAnimScene(m_pScene);
|
|
m_widgets.m_addEventSectionSelector.Select(CDebugAnimSceneSectionSelector::sm_FromTimeMarkerString); // by default, selects the section using the current time
|
|
m_widgets.m_addEventSectionSelector.AddWidgets(pBank, "Section:");
|
|
pBank->UnSetCurrentGroup(*pGroup);
|
|
|
|
m_widgets.m_eventNameList.clear();
|
|
m_widgets.m_eventNameList.PushAndGrow("Select an event to add");
|
|
|
|
eAnimSceneEntityType type = pEntity ? pEntity->GetType() : ANIM_SCENE_ENTITY_NONE;
|
|
|
|
for (s32 i=0 ;i<m_eventInitialisers.GetCount(); i++)
|
|
{
|
|
if (m_eventInitialisers[i] && m_eventInitialisers[i]->SupportsEntityType(type))
|
|
{
|
|
m_widgets.m_eventNameList.PushAndGrow(m_eventInitialisers[i]->GetFriendlyEventTypeName().GetCStr());
|
|
}
|
|
}
|
|
|
|
if(m_bAllowWidgetAutoRegen)
|
|
{
|
|
m_widgets.m_selectedEntityType = 0;
|
|
}
|
|
|
|
m_widgets.m_pEventTypeCombo = pGroup->AddCombo("Event type", (unsigned char *)(&(m_widgets.m_selectedEventType)), m_widgets.m_eventNameList.GetCount(), &(m_widgets.m_eventNameList[0]), datCallback(MFA(CAnimSceneEditor::RegenEventTypeWidgets), this), 0, NULL);
|
|
}
|
|
|
|
void CAnimSceneEditor::Selection::SelectEntity(CAnimSceneEntity* pEnt)
|
|
{
|
|
if (pEnt)
|
|
{
|
|
// deselect the selected event if it doesn't belong to the selected entity
|
|
if (m_pEvent && m_pEvent->GetPrimaryEntityId()!=pEnt->GetId())
|
|
{
|
|
m_pEvent = NULL;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (m_pEvent && m_pEvent->GetPrimaryEntityId()!=ANIM_SCENE_ENTITY_ID_INVALID)
|
|
{
|
|
m_pEvent = NULL;
|
|
}
|
|
}
|
|
|
|
m_pEntity = pEnt;
|
|
}
|
|
|
|
void CAnimSceneEditor::Selection::SelectEvent(CAnimSceneEvent* pEvt)
|
|
{
|
|
if (pEvt)
|
|
{
|
|
// deselect the selected entity if it doesn't belong to the selected event
|
|
if (m_pEntity && m_pEntity->GetId()!=pEvt->GetPrimaryEntityId())
|
|
{
|
|
m_pEntity = NULL;
|
|
}
|
|
}
|
|
|
|
m_pEvent = pEvt;
|
|
}
|
|
|
|
// Rag callbacks
|
|
void CAnimSceneEditor::TimelineDisplayModeChangedCB()
|
|
{
|
|
if (m_editorSettingTimelineDisplayMode == kTimelineDisplayMode_Frames)
|
|
{
|
|
m_timeline.SetTimeDisplayMode(COnScreenTimeline::kDisplayFrames);
|
|
}
|
|
else
|
|
{
|
|
m_timeline.SetTimeDisplayMode(COnScreenTimeline::kDisplayTimes);
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::TimelineSnapChangedCB()
|
|
{
|
|
m_timeline.SetMarkerSnapToFrames(m_editorSettingTimelineSnapToFrames);
|
|
}
|
|
|
|
void CAnimSceneEditor::InitEventInitialisers()
|
|
{
|
|
// run over the event initialiser definitions and make one of each of them
|
|
const parStructure* pEventInitialiserStruct = PARSER.FindStructure("CAnimSceneEventInitialiser");
|
|
|
|
parManager::StructureMap::ConstIterator it = PARSER.GetStructureMap().CreateIterator();
|
|
|
|
for( ; !it.AtEnd(); it.Next())
|
|
{
|
|
parStructure* pStruct = it.GetData();
|
|
if (pEventInitialiserStruct && pStruct->IsSubclassOf(pEventInitialiserStruct) && pStruct!=pEventInitialiserStruct)
|
|
{
|
|
CAnimSceneEventInitialiser* pInst = (CAnimSceneEventInitialiser*)pStruct->Create();
|
|
pInst->m_pEditor = this;
|
|
// instantiate an initialiser and add it to the list
|
|
m_eventInitialisers.PushAndGrow(pInst);
|
|
}
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::InitEventScrollbar()
|
|
{
|
|
m_eventsScrollbar.Init(0.f,10.f,0.f,
|
|
GetColor(kScrollBarBackgroundColour),GetColor(kTextHoverColor),CAnimSceneScrollbar::ORIENTATION_VERTICAL);
|
|
m_eventsScrollbar.SetTopLeft(Vector2(m_EventLayersWindow.GetScreenExtents().GetMinX()-20.f,m_EventLayersWindow.GetScreenExtents().GetMinY() + 10.f));
|
|
m_eventsScrollbar.SetLength(m_EventLayersWindow.GetScreenExtents().GetMaxY() - m_EventLayersWindow.GetScreenExtents().GetMinY() - 20.f);
|
|
m_eventsScrollbar.SetBarHidden(true);
|
|
}
|
|
|
|
CAnimSceneEventInitialiser* CAnimSceneEditor::GetEventInitialiserFromFriendlyName(atHashString friendlyName)
|
|
{
|
|
for (s32 i=0; i<m_eventInitialisers.GetCount(); i++)
|
|
{
|
|
if (m_eventInitialisers[i]->GetFriendlyEventTypeName()==friendlyName)
|
|
{
|
|
return m_eventInitialisers[i];
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
CAnimSceneEventInitialiser* CAnimSceneEditor::GetEventInitialiser(atHashString eventClassName)
|
|
{
|
|
for (s32 i=0; i<m_eventInitialisers.GetCount(); i++)
|
|
{
|
|
if (m_eventInitialisers[i]->GetEventTypeName()==eventClassName)
|
|
{
|
|
return m_eventInitialisers[i];
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
void CAnimSceneEditor::CleanupEventInitialiserWidgets()
|
|
{
|
|
for (s32 i=0;i<m_eventInitialisers.GetCount(); i++)
|
|
{
|
|
if (m_eventInitialisers[i]->m_bRequiresWidgetCleanup)
|
|
{
|
|
m_eventInitialisers[i]->RemoveWidgets(m_widgets.m_pAddEventGroup, this);
|
|
m_eventInitialisers[i]->m_bRequiresWidgetCleanup = false;
|
|
}
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::InitEntityInitialisers()
|
|
{
|
|
// run over the event initialiser definitions and make one of each of them
|
|
const parStructure* pInitialiserStruct = PARSER.FindStructure("CAnimSceneEntityInitialiser");
|
|
|
|
parManager::StructureMap::ConstIterator it = PARSER.GetStructureMap().CreateIterator();
|
|
|
|
for( ; !it.AtEnd(); it.Next())
|
|
{
|
|
parStructure* pStruct = it.GetData();
|
|
if (pInitialiserStruct && pStruct->IsSubclassOf(pInitialiserStruct) && pStruct!=pInitialiserStruct)
|
|
{
|
|
CAnimSceneEntityInitialiser* pInst = (CAnimSceneEntityInitialiser*)pStruct->Create();
|
|
pInst->m_pEditor = this;
|
|
// instantiate an initialiser and add it to the list
|
|
m_entityInitialisers.PushAndGrow(pInst);
|
|
}
|
|
}
|
|
}
|
|
|
|
CAnimSceneEntityInitialiser* CAnimSceneEditor::GetEntityInitialiserFromFriendlyName(atHashString friendlyName)
|
|
{
|
|
for (s32 i=0; i<m_entityInitialisers.GetCount(); i++)
|
|
{
|
|
if (m_entityInitialisers[i]->GetFriendlyEntityTypeName()==friendlyName)
|
|
{
|
|
return m_entityInitialisers[i];
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
CAnimSceneEntityInitialiser* CAnimSceneEditor::GetEntityInitialiser(atHashString eventClassName)
|
|
{
|
|
for (s32 i=0; i<m_entityInitialisers.GetCount(); i++)
|
|
{
|
|
if (m_entityInitialisers[i]->GetEntityTypeName()==eventClassName)
|
|
{
|
|
return m_entityInitialisers[i];
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
void CAnimSceneEditor::CleanupEntityInitialiserWidgets()
|
|
{
|
|
for (s32 i=0;i<m_entityInitialisers.GetCount(); i++)
|
|
{
|
|
if (m_entityInitialisers[i]->m_bRequiresWidgetCleanup)
|
|
{
|
|
m_entityInitialisers[i]->RemoveWidgets(m_widgets.m_pAddEventGroup, this);
|
|
m_entityInitialisers[i]->m_bRequiresWidgetCleanup = false;
|
|
}
|
|
}
|
|
}
|
|
|
|
bool CAnimSceneEditor::FixInvalidId(CAnimSceneEntity::Id& id)
|
|
{
|
|
const char* idStr = id.TryGetCStr();
|
|
std::string idStrS = idStr;
|
|
|
|
for(int i = 0; i < idStrS.length(); )
|
|
{
|
|
if(idStrS[i] == '\n' || idStrS[i] == '\r')
|
|
{
|
|
idStrS.erase(i,1);//Only erase this character
|
|
//Can be changed to isStrS.erase(i) to erase all characters afterwards as well.
|
|
}
|
|
else
|
|
{
|
|
++i;
|
|
}
|
|
}
|
|
|
|
id.SetFromString(idStrS.c_str());
|
|
|
|
return CAnimSceneEntity::IsValidId(id);
|
|
}
|
|
|
|
void CAnimSceneEditor::CheckAnimSceneVersion()
|
|
{
|
|
if(!m_pScene)
|
|
{
|
|
return;
|
|
}
|
|
if(m_pScene->GetVersion() != ANIM_SCENE_CURRENT_VERSION)
|
|
{
|
|
animWarningf("Anim scene is version: %d, current anim scene version is: %d", m_pScene->GetVersion(), ANIM_SCENE_CURRENT_VERSION);
|
|
}
|
|
|
|
}
|
|
|
|
void CAnimSceneEditor::RenderEventsScrollbar()
|
|
{
|
|
m_eventsScrollbar.Render();
|
|
}
|
|
|
|
bool CAnimSceneEditor::ValidateScene()
|
|
{
|
|
if(m_pScene)
|
|
{
|
|
return m_pScene->Validate();
|
|
}
|
|
return false;
|
|
}
|
|
|
|
void CAnimSceneEditor::SynchroniseHoldAtEndFlag()
|
|
{
|
|
if(m_pScene)
|
|
{
|
|
m_pScene->SetEditorHoldAtEnd(m_editorSettingHoldAtLastFrame);
|
|
}
|
|
}
|
|
|
|
void CAnimSceneEditor::LoopEditorToggleCB()
|
|
{
|
|
if(m_editorSettingLoopPlayback)
|
|
{
|
|
m_editorSettingHoldAtLastFrame = false;
|
|
SynchroniseHoldAtEndFlag();
|
|
}
|
|
}
|
|
|
|
CAnimSceneEditor::MouseState::MouseState()
|
|
: m_mouseCoords()
|
|
, m_lastMouseCoords()
|
|
, m_leftMouseDown(false)
|
|
, m_leftMousePressed(false)
|
|
, m_leftMouseReleased(false)
|
|
, m_rightMouseDown(false)
|
|
, m_rightMousePressed(false)
|
|
, m_rightMouseReleased(false)
|
|
{
|
|
|
|
}
|
|
|
|
void CAnimSceneEditor::MouseState::Update()
|
|
{
|
|
m_lastMouseCoords.x = m_mouseCoords.x;
|
|
m_lastMouseCoords.y = m_mouseCoords.y;
|
|
m_mouseCoords.x = static_cast<float>(ioMouse::GetX());
|
|
m_mouseCoords.y = static_cast<float>(ioMouse::GetY());
|
|
m_leftMouseDown = (ioMouse::GetButtons() & ioMouse::MOUSE_LEFT);
|
|
m_leftMousePressed = (ioMouse::GetPressedButtons() & ioMouse::MOUSE_LEFT);
|
|
m_leftMouseReleased = (ioMouse::GetReleasedButtons() & ioMouse::MOUSE_LEFT);
|
|
m_rightMouseDown = ((ioMouse::GetButtons() & ioMouse::MOUSE_RIGHT)!=0);
|
|
m_rightMousePressed = ((ioMouse::GetPressedButtons() & ioMouse::MOUSE_RIGHT)!=0);
|
|
m_rightMouseReleased = ((ioMouse::GetReleasedButtons() & ioMouse::MOUSE_RIGHT)!=0);
|
|
|
|
animDebugf3("[%d:%d] LMD: %s LMP: %s LMR: %s MouseX:%.3f(%.3f) MouseY:%.3f(%.3f)"
|
|
, fwTimer::GetTimeInMilliseconds(), fwTimer::GetFrameCount()
|
|
, m_leftMouseDown? "TRUE" : "FALSE"
|
|
, m_leftMousePressed? "TRUE" : "FALSE"
|
|
, m_leftMouseReleased? "TRUE" : "FALSE"
|
|
, m_mouseCoords.x, m_lastMouseCoords.x, m_mouseCoords.y, m_lastMouseCoords.y);
|
|
}
|
|
|
|
|
|
#endif // __BANK
|