void DrawRecord(RecordCoordinates recordCoordinates, TimelineWidget.DrawInfo drawInfo) { int totalY = recordCoordinates.poseY; if (recordCoordinates.trajectoryY >= 0) { totalY += recordCoordinates.trajectoryY; if (m_bDisplayTrajectoryCost) { for (int posX = recordCoordinates.startX; posX <= recordCoordinates.endX; ++posX) { GetPixel(posX, recordCoordinates.trajectoryY) = kTrajectoryCostColor; } } } for (int posX = recordCoordinates.startX; posX <= recordCoordinates.endX; ++posX) { if (m_bDisplayPoseCost) { GetPixel(posX, recordCoordinates.poseY) = kPoseCostColor; } if (m_bDisplayTotalCost) { GetPixel(posX, totalY) = kTotalCostColor; } } }
void DisplayOptions(TimelineWidget.DrawInfo drawInfo) { Rect backgroundRect = new Rect(drawInfo.layout.drawRect.x, drawInfo.timeline.drawRect.y, kOptionsRectWidth, drawInfo.timeline.drawRect.height); TimelineWidget.DrawRectangle(backgroundRect, kOptionsBackgroundColor); Rect rect = drawInfo.timeline.drawRect; rect.x = drawInfo.layout.drawRect.x + kTextHorizontalMargin; rect.y += kTextVerticalSpacing; rect.width = kOptionsRectWidth; rect.height = kTextRectHeight; GUIStyle style = GUI.skin.toggle; style.normal.textColor = kTotalCostColor; m_bDisplayTotalCost = GUI.Toggle(rect, m_bDisplayTotalCost, new GUIContent("Total cost"), style); rect.y += kTextVerticalSpacing; style.normal.textColor = kPoseCostColor; m_bDisplayPoseCost = GUI.Toggle(rect, m_bDisplayPoseCost, new GUIContent("Pose cost"), style); rect.y += kTextVerticalSpacing; style.normal.textColor = kTrajectoryCostColor; m_bDisplayTrajectoryCost = GUI.Toggle(rect, m_bDisplayTrajectoryCost, new GUIContent("Trajectory cost"), style); }
RecordCoordinates GetRecordCoordinates(DebugCostAggregate.Record record, TimelineWidget.DrawInfo drawInfo) { return(new RecordCoordinates() { startX = ClampPosX((int)math.round(drawInfo.GetPixelPosition(record.startTime) - drawInfo.timeline.drawRect.x)), endX = ClampPosX((int)math.round(drawInfo.GetPixelPosition(record.endTime) - drawInfo.timeline.drawRect.x)), poseY = ClampPosY((int)math.round(math.min(record.poseCost / m_MaxCost, 1.0f) * m_CacheTexture.height)), trajectoryY = record.trajectoryCost >= 0.0f ? ClampPosY((int)math.round(math.min(record.trajectoryCost / m_MaxCost, 1.0f) * m_CacheTexture.height)) : -1 }); }
float GetMouseTime(TimelineWidget.DrawInfo drawInfo) { Rect costTimelineRect = drawInfo.layout.drawRect; costTimelineRect.x += kOptionsRectWidth; if (costTimelineRect.Contains(Event.current.mousePosition)) { return(drawInfo.GetTime(Event.current.mousePosition.x)); } return(-1.0f); }
public void Draw(FrameDebugProviderInfo providerInfo, IFrameAggregate aggregate, TimelineWidget.DrawInfo drawInfo) { AbilityFrameAggregate abilityAggregate = (AbilityFrameAggregate)aggregate; foreach (AbilityState state in abilityAggregate.States) { float startPosition = drawInfo.GetPixelPosition(state.startTime); float endPosition = drawInfo.GetPixelPosition(state.endTime); Rect abilityRect = new Rect(startPosition, drawInfo.timeline.drawRect.y, endPosition - startPosition, kAbilityRectHeight); TimelineWidget.DrawRectangleWithDetour(abilityRect, kAbilityWidgetBackgroundColor, kAbilityWidgetDetourColor); TimelineWidget.DrawLabelInsideRectangle(abilityRect, state.abilityType.FullName, kAbilityWidgetTextColor); } }
void DisplayMouseCost(TimelineWidget.DrawInfo drawInfo) { if (m_MouseCost >= 0.0f) { float normalizedY = 1.0f - math.min(m_MouseCost / m_MaxCost, 1.0f); float y = drawInfo.timeline.drawRect.height * normalizedY + kTextRectHeight; y = math.clamp(y, 0, drawInfo.timeline.drawRect.height - kTextRectHeight); Rect mouseRect = new Rect(drawInfo.GetPixelPosition(m_MouseTime), drawInfo.timeline.drawRect.y + y, kMouseCostTextWidth, kTextRectHeight); GUIStyle style = new GUIStyle(); style.normal.textColor = kAxisColor; GUI.Label(mouseRect, new GUIContent($"{m_MouseCost:0.000}"), style); } }
void DisplayYAxis(TimelineWidget.DrawInfo drawInfo) { float startX = math.max(drawInfo.layout.drawRect.x + kOptionsRectWidth, drawInfo.timeline.drawRect.x); Rect maxVal = new Rect(startX + kAxisHorizontalTextOffset, drawInfo.timeline.drawRect.y, drawInfo.timeline.drawRect.width, kTextRectHeight); GUIStyle style = new GUIStyle(); style.normal.textColor = kAxisColor; GUI.Label(maxVal, new GUIContent($"{m_MaxCost:0.00}"), style); maxVal.y += drawInfo.timeline.drawRect.height - kTextRectHeight; GUI.Label(maxVal, new GUIContent("0"), style); TimelineWidget.DrawRectangle(new Rect(startX + kAxisHorizontalTextOffset * 0.5f, drawInfo.timeline.drawRect.y, 1.0f, drawInfo.timeline.drawRect.height), kAxisColor); TimelineWidget.DrawRectangle(new Rect(startX + kAxisHorizontalLineMargin, drawInfo.timeline.drawRect.y, kAxisHorizontalTextOffset - kAxisHorizontalLineMargin, 1.0f), kAxisColor); TimelineWidget.DrawRectangle(new Rect(startX + kAxisHorizontalLineMargin, drawInfo.timeline.drawRect.y + drawInfo.timeline.drawRect.height - 1, kAxisHorizontalTextOffset - kAxisHorizontalLineMargin, 1.0f), kAxisColor); }
public void Draw(FrameDebugProviderInfo providerInfo, IFrameAggregate aggregate, TimelineWidget.DrawInfo drawInfo) { AnimationDebugRecord animDebugRecord = (AnimationDebugRecord)aggregate; DrawAnimationTimeline(providerInfo, animDebugRecord, drawInfo); }
private void DrawAnimationWidget(FrameDebugProviderInfo providerInfo, AnimationDebugRecord animStateRecord, int animIndex, TimelineWidget.DrawInfo drawInfo) { AnimationRecord animation = animStateRecord.AnimationRecords[animIndex]; if (animation.endTime < drawInfo.timeline.startTime) { return; } if (animation.startTime > drawInfo.timeline.endTime) { return; } float startPosition = drawInfo.GetPixelPosition(animation.startTime); float endPosition = drawInfo.GetPixelPosition(animation.endTime); Rect drawRect = drawInfo.timeline.drawRect; drawRect.y += animation.rank * kAnimWidgetOffset; Rect animRect = new Rect(startPosition, drawRect.y, endPosition - startPosition, kAnimWidgetHeight); TimelineWidget.DrawRectangleWithDetour(animRect, kAnimWidgetBackgroundColor, kAnimWidgetDetourColor); int barStartPosition = Missing.truncToInt(startPosition) + 1; int maxBarPosition = Missing.truncToInt(endPosition); for (int i = 0; i < animation.animFrames.Count; ++i) { int barEndPosition = Missing.truncToInt(drawInfo.GetPixelPosition(animation.animFrames[i].endTime)); if (barEndPosition > barStartPosition) { float weight = animation.animFrames[i].weight; if (weight < 1.0f) { Rect barRect = new Rect(barStartPosition, drawRect.y, barEndPosition - barStartPosition, (1.0f - weight) * kAnimWidgetHeight); TimelineWidget.DrawRectangle(barRect, kAnimWidgetWeightColor); } } barStartPosition = barEndPosition; } TimelineWidget.DrawLabelInsideRectangle(animRect, animation.animName, kAnimWidgetTextColor); // check if mouse is hovering the anim widget if (endPosition > startPosition && animRect.Contains(Event.current.mousePosition)) { float mouseNormalizedTime = (Event.current.mousePosition.x - startPosition) / (endPosition - startPosition); float mouseTime = animation.startTime + mouseNormalizedTime * (animation.endTime - animation.startTime); float curStartTime = animation.startTime; for (int i = 0; i < animation.animFrames.Count; ++i) { float curEndTime = animation.animFrames[i].endTime; if (curStartTime <= mouseTime && mouseTime <= curEndTime) { m_SelectedAnimFrame.providerIdentifier = providerInfo.uniqueIdentifier; m_SelectedAnimFrame.animIndex = animIndex; m_SelectedAnimFrame.animFrameIndex = i; m_SelectedAnimFrame.mouseX = Missing.truncToInt(Event.current.mousePosition.x); return; } curStartTime = curEndTime; } } }
private void DrawAnimationTimeline(FrameDebugProviderInfo providerInfo, AnimationDebugRecord animStateRecord, TimelineWidget.DrawInfo drawInfo) { if (animStateRecord.AnimationRecords.Count == 0) { return; } // Animations for (int i = 0; i < animStateRecord.AnimationRecords.Count; ++i) { DrawAnimationWidget(providerInfo, animStateRecord, i, drawInfo); } }
void DrawCostTimeline(FrameDebugProviderInfo providerInfo, IFrameAggregate aggregate, TimelineWidget.DrawInfo drawInfo) { Rect selectedRect = drawInfo.timeline.drawRect; int width = (int)selectedRect.width; int height = (int)selectedRect.height; if (width * height == 0) { return; } if (aggregate.IsEmpty) { return; } IMotionSynthesizerProvider synthesizerProvider = providerInfo.provider as IMotionSynthesizerProvider; if (synthesizerProvider == null || !synthesizerProvider.IsSynthesizerInitialized) { return; } DebugMemory debugMemory = synthesizerProvider.Synthesizer.Ref.ReadDebugMemory; foreach (SelectedFrameDebugProvider selected in Debugger.frameDebugger.Selection) { if (selected.providerInfo.uniqueIdentifier == providerInfo.uniqueIdentifier) { CreateAndClearTexture(width, height); if (selected.metadata != null) { DebugIdentifier selectedIdentifier = (DebugIdentifier)selected.metadata; DebugReference reference = debugMemory.FindObjectReference(selectedIdentifier); if (reference.IsValid) { object selectedObject = debugMemory.ReadObjectGeneric(reference); if (selectedObject is IMotionMatchingQuery query) { DrawCostTimeline(query.DebugName.GetHashCode(), (DebugCostAggregate)aggregate, drawInfo); } if (selectedObject is IDisposable disposable) { disposable.Dispose(); } } } m_CacheTexture.SetPixels(m_CachePixels); m_CacheTexture.Apply(); GUI.DrawTexture(selectedRect, m_CacheTexture); return; } } }
void DrawRecord(RecordCoordinates recordCoordinates, RecordCoordinates prevRecordCoordinates, TimelineWidget.DrawInfo drawInfo) { DrawRecord(recordCoordinates, drawInfo); int prevTotalY = prevRecordCoordinates.poseY; int totalY = recordCoordinates.poseY; if (recordCoordinates.trajectoryY >= 0) { if (m_bDisplayTrajectoryCost) { DrawVerticalLine(new int2(prevRecordCoordinates.endX, prevRecordCoordinates.trajectoryY), new int2(recordCoordinates.startX, recordCoordinates.trajectoryY), kTrajectoryCostColor); } prevTotalY += prevRecordCoordinates.trajectoryY; totalY += recordCoordinates.trajectoryY; } if (m_bDisplayPoseCost) { DrawVerticalLine(new int2(prevRecordCoordinates.endX, prevRecordCoordinates.poseY), new int2(recordCoordinates.startX, recordCoordinates.poseY), kPoseCostColor); } if (m_bDisplayTotalCost) { DrawVerticalLine(new int2(prevRecordCoordinates.endX, prevTotalY), new int2(recordCoordinates.startX, totalY), kTotalCostColor); } }
public void Draw(FrameDebugProviderInfo providerInfo, IFrameAggregate aggregate, TimelineWidget.DrawInfo drawInfo) { if (!enabled) { return; } DrawCostTimeline(providerInfo, aggregate, drawInfo); DisplayOptions(drawInfo); DisplayYAxis(drawInfo); DisplayMouseCost(drawInfo); }
void DrawCostTimeline(int queryIdentifier, DebugCostAggregate aggregate, TimelineWidget.DrawInfo drawInfo) { m_MouseTime = GetMouseTime(drawInfo); m_MouseCost = -1.0f; (DebugCostAggregate.Record, RecordCoordinates) ? prevRecord = null; m_MaxCost = kDefaultMaxCost; for (int index = 0; index < aggregate.NumRecords; ++index) { DebugCostAggregate.Record record = aggregate.GetRecord(index); if (record.queryIdentifier != queryIdentifier || record.endTime <= drawInfo.timeline.startTime) { continue; } if (record.startTime >= drawInfo.timeline.endTime) { break; } m_MaxCost = math.max(m_MaxCost, record.poseCost); if (record.trajectoryCost >= 0.0f) { m_MaxCost = math.max(m_MaxCost, record.TotalCost); } if (m_MouseTime >= 0.0f && m_MouseTime >= record.startTime && m_MouseTime <= record.endTime) { if (m_bDisplayTotalCost) { m_MouseCost = record.TotalCost; } else if (m_bDisplayPoseCost) { m_MouseCost = record.poseCost; } else if (m_bDisplayTrajectoryCost) { m_MouseCost = record.trajectoryCost; } else { m_MouseCost = -1.0f; } } } for (int index = 0; index < aggregate.NumRecords; ++index) { DebugCostAggregate.Record record = aggregate.GetRecord(index); if (record.queryIdentifier != queryIdentifier || record.endTime <= drawInfo.timeline.startTime) { continue; } if (record.startTime >= drawInfo.timeline.endTime) { break; } RecordCoordinates recordCoordinates = GetRecordCoordinates(record, drawInfo); if (prevRecord.HasValue && prevRecord.Value.Item1.endTime == record.startTime) { DrawRecord(recordCoordinates, prevRecord.Value.Item2, drawInfo); } else { DrawRecord(recordCoordinates, drawInfo); } prevRecord = (record, recordCoordinates); } }
void DrawDebuggerTimeline() { IEnumerable <FrameDebugProviderInfo> providers = Debugger.frameDebugger.NumSelected == 0 ? Debugger.frameDebugger.ProviderInfos : Debugger.frameDebugger.Selection.Select(p => p.providerInfo); var lastRect = GUILayoutUtility.GetLastRect(); Rect rt = GUILayoutUtility.GetRect(lastRect.width, 54); List <float> timelineHeights = new List <float>(); foreach (FrameDebugProviderInfo provider in providers) { timelineHeights.Add(kCharacterNameOffset); rt.height += kCharacterNameOffset; List <IFrameAggregate> frameAggregates = Debugger.frameDebugger.GetFrameAggregates(provider.uniqueIdentifier); foreach (IFrameAggregate frameAggregate in frameAggregates) { float timelineHeight = m_CustomDrawers[frameAggregate.GetType()].GetDrawHeight(frameAggregate); timelineHeights.Add(timelineHeight); rt.height += timelineHeight; } } GUI.BeginGroup(rt); { Rect rect = new Rect(0, 0, rt.width, rt.height); if (m_BackgroundColor == Color.white) { m_BackgroundColor = EditorGUIUtility.isProSkin ? new Color(0.12f, 0.12f, 0.12f, 0.78f) : new Color(0.66f, 0.66f, 0.66f, 0.78f); } GUI.color = m_BackgroundColor; GUI.DrawTexture(rect, EditorGUIUtility.whiteTexture); TimelineWidget.DrawInfo drawInfo = TimelineWidget.DrawInfo.Create(rect, m_DebuggerTimeline.RangeStart, m_DebuggerTimeline.RangeEnd, m_DebuggerTimeline.SelectedRangeStart, m_DebuggerTimeline.SelectedRangeEnd); drawInfo.layout = new TimelineWidget.DrawRangeInfo() { drawRect = rect, startTime = m_DebuggerTimeline.RangeStart, endTime = m_DebuggerTimeline.RangeEnd }; drawInfo.timeline.drawRect.y += kBeginOffset; int timelineIndex = 0; Color highlightColor = Debugger.instance.rewind ? new Color(0.0f, 0.25f, 0.5f, 0.1f) : new Color(0.8f, 0.0f, 0.0f, 0.2f); if (providers.Count() > 0) { foreach (FrameDebugProviderInfo provider in providers) { List <IFrameAggregate> frameAggregates = Debugger.frameDebugger.GetFrameAggregates(provider.uniqueIdentifier); // Display name string displayName = provider.displayName; drawInfo.timeline.drawRect.height = kCharacterNameRectangleHeight; Vector2 labelSize = TimelineWidget.GetLabelSize(displayName); Rect displayNameRect = drawInfo.timeline.drawRect; displayNameRect.x = drawInfo.layout.drawRect.x; displayNameRect.width = drawInfo.layout.drawRect.width; TimelineWidget.DrawRectangle(displayNameRect, new Color(0.1f, 0.1f, 0.1f, 1.0f)); TimelineWidget.DrawLabel(new Rect(displayNameRect.x + 10.0f, displayNameRect.y, labelSize.x, kCharacterNameRectangleHeight), displayName, Color.white); drawInfo.timeline.drawRect.y += timelineHeights[timelineIndex++]; drawInfo.timeline.drawRect.height = 0.0f; int providerTimelineIndex = timelineIndex; foreach (IFrameAggregate frameAggregate in frameAggregates) { drawInfo.timeline.drawRect.height += timelineHeights[providerTimelineIndex++]; } Rect highlightRect = new Rect(drawInfo.GetPixelPosition(m_DebuggerTimeline.SelectedRangeStart) - 2.0f, drawInfo.timeline.drawRect.y - 2.0f, drawInfo.GetPixelPosition(m_DebuggerTimeline.SelectedRangeEnd) - drawInfo.GetPixelPosition(m_DebuggerTimeline.SelectedRangeStart) + 4.0f, drawInfo.timeline.drawRect.height + 2.0f); TimelineWidget.DrawRange(highlightRect, highlightColor); foreach (IFrameAggregate frameAggregate in frameAggregates) { float timelineHeight = timelineHeights[timelineIndex++]; drawInfo.timeline.drawRect.height = timelineHeight; m_CustomDrawers[frameAggregate.GetType()].Draw(provider, frameAggregate, drawInfo); drawInfo.timeline.drawRect.y += timelineHeight; } if (Debugger.instance.IsState(Debugger.State.Record)) { TimelineWidget.DrawRectangleDetour(highlightRect, Color.red, 2.0f); } } } else { Rect highlightRect = new Rect(drawInfo.GetPixelPosition(m_DebuggerTimeline.SelectedRangeStart) - 2.0f, drawInfo.layout.drawRect.y, drawInfo.GetPixelPosition(m_DebuggerTimeline.SelectedRangeEnd) - drawInfo.GetPixelPosition(m_DebuggerTimeline.SelectedRangeStart) + 4.0f, drawInfo.layout.drawRect.height); TimelineWidget.DrawRange(highlightRect, highlightColor); if (Debugger.instance.IsState(Debugger.State.Record)) { TimelineWidget.DrawRectangleDetour(highlightRect, Color.red, 2.0f); } } TimelineWidget.DrawNotations(drawInfo); m_DebuggerTimeline.Update(rect, Debugger.instance.rewind ? -1.0f : Debugger.instance.time); var debugger = Debugger.instance; if (Application.isPlaying) { Color cursorColor = new Color(0.5f, 0.5f, 0.0f, 1.0f); TimelineWidget.DrawLineAtTime( drawInfo, debugger.rewindTime, cursorColor); } foreach (var drawer in m_CustomDrawers) { drawer.Value.OnPostDraw(); } if (debugger.isActive) { if (rect.Contains(Event.current.mousePosition)) { var e = Event.current; if (e.button == 0 && !e.alt) { if (e.type == EventType.MouseDrag || e.type == EventType.MouseDown || e.type == EventType.MouseUp) { e.Use(); m_DebuggerTimeline.Repaint = true; EditorGUIUtility.AddCursorRect(rect, MouseCursor.Arrow); float currentTime = m_DebuggerTimeline.GetCurrentPositionFromMouse( rect, Event.current.mousePosition); float start = m_DebuggerTimeline.SelectedRangeStart; float end = m_DebuggerTimeline.SelectedRangeEnd; debugger.rewindTime = Mathf.Clamp(currentTime, start, end); debugger.rewind = debugger.rewind || currentTime <= end; } } } } GUI.EndGroup(); } GUILayout.Space(5 + rt.height); }