@Model.Book.BookDisplayTitle · Chapter @Model.Chapter.ChapterNumber.ToString("0.##") · Scene @scene.SceneNumber.ToString("0.##")
@scene.SceneTitle
@if (scene.StartDateTime.HasValue) { @scene.StartDateTime.Value.ToString("dddd, d MMMM yyyy", CultureInfo.GetCultureInfo("en-GB")) @if (exactTime) { · @scene.StartDateTime.Value.ToString("h:mm tt", CultureInfo.GetCultureInfo("en-GB")) } } else { Story date unknown } @if (!string.IsNullOrWhiteSpace(scene.RelativeTimeText)) { · @scene.RelativeTimeText } · @scene.TimeModeName
POV: @(Model.PovName ?? "Not recorded") · Location: @(Model.Location?.LocationPath ?? scene.PrimaryLocationName ?? "Not recorded")
Characters present @Model.Characters.Count
@if (Model.Characters.Count == 0) {No characters attached to this scene.
} else {| Character | Age at this point | Known location | Previous appearance |
|---|---|---|---|
| @person.Appearance.CharacterName @string.Join(" · ", new[] { person.Appearance.RoleInSceneTypeName, person.Appearance.PresenceTypeName }.Where(x => !string.IsNullOrWhiteSpace(x)).Distinct(StringComparer.OrdinalIgnoreCase)) | @(person.Age.DisplayText ?? "Unknown") @if (!person.Age.HasExactAge && person.Age.DisplayText is not null) { Approximate } | @(person.State?.CurrentLocation ?? "Unknown")@(person.State?.State == "Inferred" ? "Last known" : "") | @if (person.PreviousAppearance is { } previous) { @previous.Label } else { First recorded appearance } |
Character knowledge
@if (Model.Characters.All(x => x.Knowledge.Count == 0)) {No structured knowledge recorded by this point.
} @foreach (var person in Model.Characters.Where(x => x.Knowledge.Count > 0)) {@person.Appearance.CharacterName
-
@foreach (var fact in person.Knowledge) {
- @fact.KnowledgeStateName: @(string.IsNullOrWhiteSpace(fact.Description) ? fact.AssetName ?? fact.ThreadTitle ?? "Recorded fact" : fact.Description) @(Model.Sources.GetValueOrDefault(fact.SceneID)?.Label ?? "Source scene") }
Relationships at this point
@if (Model.Relationships.Count == 0) {No historically established relationships recorded for these characters.
}- @foreach (var relationship in Model.Relationships) {
var source = relationship.History.LastOrDefault(x => x.SceneID.HasValue);
- @relationship.CharacterAName ↔ @relationship.CharacterBName@relationship.CurrentStateName@if (source?.SceneID is int sourceId) { @(Model.Sources.GetValueOrDefault(sourceId)?.Label ?? "Source scene") } else { Established at story start }
}
Assets / important objects
@if (Model.Assets.Count == 0) {No relevant assets recorded by this point.
} else {| Asset | Holder | Location | Status | Last recorded event |
|---|---|---|---|---|
| @asset.AssetName | @asset.Holder | @asset.Location | @asset.Status | @asset.LatestEvent @if (asset.LastConfirmedSceneID is int sourceId) { @(Model.Sources.GetValueOrDefault(sourceId)?.Label ?? "Source scene") } |
Location state
@if (Model.Location is { } location) {@location.LocationPath
People last known here: @(location.CharactersPresent.Count == 0 ? "None recorded" : string.Join(", ", location.CharactersPresent))
Assets last known here: @(location.AssetsPresent.Count == 0 ? "None recorded" : string.Join(", ", location.AssetsPresent))
@if (Model.PreviousLocationUse is { } previous) {Previous scene here: @previous.Label
} } else {No primary location recorded.
}Active threads / questions / clues
@if (Model.Threads.Count == 0) {No active threads established by this point.
}- @foreach (var thread in Model.Threads) {
- @thread.Title @thread.Type · @thread.State @if (thread.Source is { } source) { @source.Label } }
Things worth checking at this point
@if (Model.Warnings.Count == 0) {No relevant continuity warnings.
}- @foreach (var warning in Model.Warnings) {
- @warning.Severity: @warning.Message @if (warning.SceneID is int sourceId) { @(Model.Sources.GetValueOrDefault(sourceId)?.Label ?? "Source scene") } }