You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
docs(profiler-markers): one example type, generated-code block, minimal sample section
- quick start now uses FlockSimulation like the rest of the page
- Profiler screenshot replaces the ASCII tree; the duplicate "Result in Profiler" section becomes a one-line "Package sample"
- collapsible generated-code example under Step(); line-number and ENABLE_PROFILER bullets shortened
- drop the using/IDisposable semantics sentence (Unity behaviour, not FastTools)
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
`this.Marker()`automatically creates a Unity Profiler marker.
3
+
`this.Marker()` creates a Unity Profiler marker named `Type.Method (line)` — no static `ProfilerMarker` field and no hand-typed name.
4
4
5
5
## Quick start
6
6
7
+
The examples on this page work with the `FlockSimulation` class from the [ProfilerMarkers sample](../Samples~/ProfilerMarkers/Documentation/README.md):
8
+
7
9
| Before — Unity API | After — FastTools |
8
10
|---|---|
9
-
| <prelang="csharp"><code>private static readonly ProfilerMarker UpdateMarker = new("MotionSimulation.Update"); private void Update() { using var _ = UpdateMarker.Auto(); Simulate(); }</code></pre> | <prelang="csharp"><code>private void Update() { using var _ = this.Marker(); Simulate(); }</code></pre> |
11
+
| <prelang="csharp"><code>private static readonly ProfilerMarker StepMarker = new("FlockSimulation.Step"); public void Step() { using var _ = StepMarker.Auto(); Integrate(); }</code></pre> | <prelang="csharp"><code>public void Step() { using var _ = this.Marker(); Integrate(); }</code></pre> |
10
12
11
-
Works in `MonoBehaviour` and ordinary C# classes. The generator ships with the package; the extension is in the global namespace — no extra `using`, attributes, or `partial` declaration needed. The marker is named `Type.Method (line)`.
13
+
Works in `MonoBehaviour` and ordinary C# classes. The generator ships with the package; the extension is in the global namespace — no extra `using`, attributes, or `partial` declaration needed.
12
14
13
15
## Scope and names
14
16
15
-
`Marker()` returns a `ProfilerMarker.AutoScope`: measurement starts at the call and ends when leaving `using`, including on `return` or an exception. `.WithName("Steering")` replaces the method part of the name; the type and line number remain.
17
+
`Marker()` returns a `ProfilerMarker.AutoScope`. `.WithName("Steering")` replaces the method part of the name; the type and line number remain.
16
18
17
19
```csharp
18
20
publicvoidStep()
@@ -35,35 +37,54 @@ public void Step()
35
37
}
36
38
```
37
39
38
-
In the Profiler with 120 loop iterations:
40
+
<details>
41
+
<summary>Generated code</summary>
42
+
43
+
Abridged: without `global::` and the repeated attribute. Line numbers count from the top of the block above; in a real file they are source-file lines.
`WithName` accepts only a string literal: `"Steering"`, `@"Steering"`, or `$"Steering"` without substitutions. Variables, `const`, `nameof`, concatenation, and `$"Agent {index}"` keep the original method name — the generator reads the source text and does not evaluate expressions. The argument is still evaluated at runtime.
68
+
</details>
48
69
49
-
> [!IMPORTANT]
50
-
> Do not call `this.Marker()` without `using`: measurement will not end automatically. Scopes must not cross `await` or `yield`; measure synchronous sections separately ([Unity limitation](https://docs.unity3d.com/6000.0/Documentation/Manual/profiler-add-markers-code.html)).
70
+
The tree in **CPU Usage → Hierarchy** mirrors the `using` nesting, and a marker inside a loop stays a single row with a `Calls` count. Deep Profile is not needed.
51
71
52
-
## Generation details
72
+

53
73
54
-
-**Line number.** The marker is selected by `CallerLineNumber`, so each call within a type needs its own line, including across `partial` files. Moving the call changes the name suffix.
55
-
-**Lambdas and local functions** use the nearest declared member: `Ctor` for constructors, the property name for accessors.
56
-
-**Generic types** get separate markers per closed type: `Worker<int>.Run()` → `Worker<Int32>.Run (line)`.
57
-
-**Without `ENABLE_PROFILER`** the extension returns `default`: nothing is measured, the code inside `using` still runs, `WithName` arguments are still evaluated.
74
+
FlockSimulation markers in CPU Usage: Steering and Integrate nested under Step, Steering.Agent with 120 calls
58
75
59
-
<aid="result"></a>
76
+
`WithName` accepts only a string literal: `"Steering"`, `@"Steering"`, or `$"Steering"` without substitutions. Variables, `const`, `nameof`, concatenation, and `$"Agent {index}"` keep the original method name — the generator reads the source text and does not evaluate expressions. The argument is still evaluated at runtime.
60
77
61
-
## Result in the Profiler
78
+
> [!IMPORTANT]
79
+
> Do not call `this.Marker()` without `using`: the measurement will not end automatically. A scope must not cross `await` or `yield`; measure synchronous sections separately ([Unity limitation](https://docs.unity3d.com/6000.0/Documentation/Manual/profiler-add-markers-code.html)).
62
80
63
-
Open **Window → Analysis → Profiler**, enable recording, and run the scene. Select a frame in **CPU Usage → Hierarchy** and search for the type name. Deep Profile is not required.
81
+
## Generation details
64
82
65
-

83
+
-**Line number.** Every call in a type needs its own line, including across `partial` files. Moving a call changes the name suffix.
84
+
-**Member name.** A method contributes its own name, a constructor `Ctor`, a property accessor the property name. Lambdas and local functions use the member they are declared in.
85
+
-**Generic types** get separate markers per closed type: `Worker<int>.Run()` → `Worker<Int32>.Run (line)`.
86
+
-**Without `ENABLE_PROFILER`** nothing is measured, but the code inside `using` and the `WithName` arguments still run.
66
87
67
-
Flock and FlockSimulation markers in CPU Usage: Steering.Agent has 120 calls
88
+
## Package sample
68
89
69
-
To reproduce this, import the [ProfilerMarkers sample](../Samples~/ProfilerMarkers/Documentation/README.md#try), open `Scenes/ProfilerMarkers.unity`, and search for `Flock`. Timings depend on the frame and machine.
90
+
A flock scene with 120 agents where `FlockSimulation` carries the markers shown above: [ProfilerMarkers](../Samples~/ProfilerMarkers/Documentation/README.md).
`this.Marker()`автоматически создаёт маркер Unity Profiler.
3
+
`this.Marker()` создаёт маркер Unity Profiler с именем `Тип.Метод (строка)` — без статического поля `ProfilerMarker` и без имени, набранного руками.
4
4
5
5
## Быстрый старт
6
6
7
+
Примеры на этой странице работают с классом `FlockSimulation` из [примера ProfilerMarkers](../../Samples~/ProfilerMarkers/Documentation/README.ru.md):
8
+
7
9
| До — Unity API | После — FastTools |
8
10
|---|---|
9
-
| <prelang="csharp"><code>private static readonly ProfilerMarker UpdateMarker = new("MotionSimulation.Update"); private void Update() { using var _ = UpdateMarker.Auto(); Simulate(); }</code></pre> | <prelang="csharp"><code>private void Update() { using var _ = this.Marker(); Simulate(); }</code></pre> |
11
+
| <prelang="csharp"><code>private static readonly ProfilerMarker StepMarker = new("FlockSimulation.Step"); public void Step() { using var _ = StepMarker.Auto(); Integrate(); }</code></pre> | <prelang="csharp"><code>public void Step() { using var _ = this.Marker(); Integrate(); }</code></pre> |
10
12
11
-
Работает в `MonoBehaviour` и обычных C#-классах. Генератор входит в пакет; расширение находится в глобальном пространстве имён — дополнительные `using`, атрибуты и `partial` не нужны. Маркер называется `Тип.Метод (строка)`.
13
+
Работает в `MonoBehaviour` и обычных C#-классах. Генератор входит в пакет; расширение находится в глобальном пространстве имён — дополнительные `using`, атрибуты и `partial` не нужны.
12
14
13
15
## Область и имя
14
16
15
-
`Marker()` возвращает `ProfilerMarker.AutoScope`: замер начинается при вызове и завершается при выходе из `using`, включая `return` и исключения. `.WithName("Steering")` заменяет часть имени с методом; тип и номер строки остаются.
17
+
`Marker()` возвращает `ProfilerMarker.AutoScope`. `.WithName("Steering")` заменяет часть имени с методом; тип и номер строки остаются.
16
18
17
19
```csharp
18
20
publicvoidStep()
@@ -35,35 +37,54 @@ public void Step()
35
37
}
36
38
```
37
39
38
-
В Profiler при 120 итерациях цикла:
40
+
<details>
41
+
<summary>Сгенерированный код</summary>
42
+
43
+
Сокращённо: без `global::` и повторов атрибута. Номера строк считаются от начала блока выше; в реальном файле это строки исходника.
Дерево в **CPU Usage → Hierarchy** повторяет вложенность `using`, а маркер внутри цикла остаётся одной строкой со счётчиком `Calls`. Deep Profile не нужен.
71
+
72
+

73
+
74
+
Маркеры FlockSimulation в CPU Usage: Steering и Integrate вложены в Step, у Steering.Agent — 120 вызовов
75
+
47
76
`WithName` принимает только строковый литерал: `"Steering"`, `@"Steering"` или `$"Steering"` без подстановок. Переменные, `const`, `nameof`, конкатенация и `$"Agent {index}"` оставляют исходное имя метода — генератор читает текст исходника и не вычисляет выражения. Сам аргумент во время выполнения всё равно вычисляется.
48
77
49
78
> [!IMPORTANT]
50
79
> Не вызывайте `this.Marker()` без `using`: замер не завершится автоматически. Область не должна пересекать `await` или `yield`; измеряйте синхронные участки отдельно ([ограничение Unity](https://docs.unity3d.com/6000.0/Documentation/Manual/profiler-add-markers-code.html)).
51
80
52
81
## Особенности генерации
53
82
54
-
-**Номер строки.**Маркер выбирается по `CallerLineNumber`, поэтому каждому вызову в типе нужна своя строка, в том числе в разных файлах `partial`. Перенос вызова меняет суффикс имени.
55
-
-**Лямбды и локальные функции**используют ближайший объявленный член: `Ctor` для конструктора, имя свойства для аксессора.
83
+
-**Номер строки.**Каждому вызову в типе нужна своя строка, в том числе в разных файлах `partial`. Перенос вызова меняет суффикс имени.
84
+
-**Имя члена.**Метод даёт своё имя, конструктор — `Ctor`, аксессор свойства — имя свойства. Лямбды и локальные функции используют член, в котором объявлены.
56
85
-**Generic-типы** получают отдельные маркеры на каждый закрытый тип: `Worker<int>.Run()` → `Worker<Int32>.Run (строка)`.
57
-
-**Без `ENABLE_PROFILER`** расширение возвращает `default`: ничего не измеряется, код внутри `using` выполняется, аргументы `WithName` по-прежнему вычисляются.
58
-
59
-
<aid="result"></a>
60
-
61
-
## Результат в Profiler
62
-
63
-
Откройте **Window → Analysis → Profiler**, включите запись и запустите сцену. Выберите кадр в **CPU Usage → Hierarchy** и найдите имя типа. Deep Profile не нужен.
64
-
65
-

86
+
-**Без `ENABLE_PROFILER`** ничего не измеряется, но код внутри `using` и аргументы `WithName` по-прежнему выполняются.
66
87
67
-
Маркеры Flock и FlockSimulation в CPU Usage: у Steering.Agent — 120 вызовов
88
+
## Пример в пакете
68
89
69
-
Чтобы повторить, импортируйте [пример ProfilerMarkers](../../Samples~/ProfilerMarkers/Documentation/README.ru.md#попробуйте), откройте `Scenes/ProfilerMarkers.unity` и найдите `Flock`. Время зависит от кадра и машины.
90
+
Сцена со стаей из 120 агентов, где `FlockSimulation` размечен показанными выше маркерами: [ProfilerMarkers](../../Samples~/ProfilerMarkers/Documentation/README.ru.md).
0 commit comments