| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880 |
- #include <Windows.h>
- #include <array>
- #include <limits>
- #include <optional>
- #include <span>
- #include "../../middleware/bap/activity_message/sensor_auth_update.h"
- #include "../../state/activity/runtime.h"
- #include "activity_sdk_behavior_scope.h"
- #include "activity_sdk_mission_internal.h"
- #include "activity_sdk_scene_spawn.h"
- #include "activity_sdk_scriptable_route.h"
- #include "host_runtime.h"
- namespace sunrise::server::activity::activity_sdk_mission {
- namespace {
- namespace auth = middleware::bap::activity_message::scriptable_auth;
- namespace layouts = state::build_data::scenarios;
- namespace message = middleware::bap::activity_message::sensor_auth_update;
- namespace sdk = state::activity_sdk;
- namespace sdk_route = server::activity::activity_sdk_scriptables;
- using detail::binding_status;
- using detail::lease_status;
- using detail::materialize_plan;
- using detail::prepare_dialogue;
- using detail::prepare_directive;
- using detail::prepare_objective;
- using detail::prepare_scene;
- using detail::prepare_task;
- using detail::prepare_typed_behavior;
- using detail::PreparedScene;
- using detail::read_lease;
- using detail::same_plan;
- using detail::scene_binding_status;
- } // namespace
- /** Resolves the generated plan and current lease without changing transport state. */
- Status query(const sdk::BoundView& view, Snapshot& output) noexcept {
- output = {};
- server::bap::ActivityLinkView link{};
- const Status binding = binding_status(view, link);
- if (binding != Status::ready) {
- return binding;
- }
- output.activityClientGeneration = link.activityClientGeneration;
- output.arrivalSliceSetIndex = link.arrivalSliceSetIndex;
- output.liveSliceSetIndex = link.sliceSetIndex;
- output.effectiveRegion = link.effectiveRegion;
- server::bap::ActivityMissionSeedLeaseView lease{};
- const Status leaseResult = read_lease(view, link, lease);
- if (leaseResult != Status::ready) {
- return leaseResult;
- }
- output.revision = lease.revision;
- output.publishedRevision = lease.publishedRevision;
- output.configured = lease.configured;
- output.publicationPending = lease.publicationPending;
- output.regionArrivalPending = lease.regionArrivalPending;
- server::bap::ActivityMissionSeedPlan generated{};
- const std::int32_t selectedRegion =
- lease.configured
- && lease.plan.effectiveRegion
- <= static_cast<std::uint32_t>((std::numeric_limits<std::int32_t>::max)())
- ? static_cast<std::int32_t>(lease.plan.effectiveRegion)
- : link.effectiveRegion;
- // The lease's own omissions produced its plan, so the check must re-materialize with them.
- const Status generatedStatus = materialize_plan(
- view,
- selectedRegion,
- std::span(lease.plan.omissions).first(lease.configured ? lease.plan.omissionCount : 0),
- generated);
- output.plan = lease.configured ? lease.plan : generated;
- if (generatedStatus != Status::ready) {
- return generatedStatus;
- }
- if (lease.configured && !same_plan(lease.plan, generated)) {
- return lease.plan.effectiveRegion == generated.effectiveRegion ? Status::refused
- : Status::wrongSliceSet;
- }
- return Status::ready;
- }
- /** Selects one exact authored state and exposes its asynchronous publication state. */
- Status select_state(const sdk::BoundView& view,
- std::int32_t effectiveRegion,
- std::span<const sdk::MissionSeedOmission> omissions,
- Snapshot& output) noexcept {
- output = {};
- server::bap::ActivityLinkView link{};
- const Status binding = binding_status(view, link);
- if (binding != Status::ready) {
- return binding;
- }
- server::bap::ActivityMissionSeedPlan plan{};
- const Status materialized = materialize_plan(view, effectiveRegion, omissions, plan);
- if (materialized != Status::ready) {
- return materialized;
- }
- const Status selected = lease_status(server::bap::select_activity_mission_seed(
- view.binding, plan, link.activityClientGeneration));
- if (selected != Status::ready) {
- return selected;
- }
- return query(view, output);
- }
- /** Checks one exact occurrence and type-43 slot without changing transport state. */
- SceneStatus authored_scene_availability(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- return prepare_scene(view, occurrenceRow, slotRow, prepared);
- }
- /** Queues the next generation for one exact state-local authored scene. */
- SceneStatus activate_authored_scene(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_scene(view, occurrenceRow, slotRow, prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- if (prepared.omittedParticipants != 0) {
- log_omitted_participants(*view.catalog, slotRow, prepared.omittedParticipants);
- }
- if (server::bap::request_activity_state_local_authored_scene_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- prepared.effectiveRegion,
- prepared.activityClientGeneration,
- nullptr,
- prepared.sceneDependencies)) {
- return SceneStatus::queued;
- }
- return SceneStatus::refused;
- }
- /** Checks one exact SDK-bounded authored dialogue cue. */
- SceneStatus dialogue_cue_availability(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- std::uint16_t cueIndex) noexcept {
- PreparedScene prepared{};
- std::uint16_t authoredCueCount = 0;
- return prepare_dialogue(view, occurrenceRow, slotRow, cueIndex, prepared, authoredCueCount);
- }
- /** Queues one authored dialogue cue through the dedicated type-53 encoder. */
- SceneStatus play_dialogue_cue(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- std::uint16_t cueIndex) noexcept {
- PreparedScene prepared{};
- std::uint16_t authoredCueCount = 0;
- const SceneStatus status =
- prepare_dialogue(view, occurrenceRow, slotRow, cueIndex, prepared, authoredCueCount);
- if (status != SceneStatus::ready) {
- return status;
- }
- if (server::bap::request_activity_state_local_dialogue_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- cueIndex,
- authoredCueCount,
- prepared.effectiveRegion,
- prepared.activityClientGeneration)) {
- return SceneStatus::queued;
- }
- return SceneStatus::refused;
- }
- /** Checks one exact type-68 slot; the answer holds for every element the slot carries. */
- SceneStatus directives_availability(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- return prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kDirectiveSlotType,
- sdk::format::kDirectiveComponentClass,
- sdk::format::kDirectiveAuthSchema,
- false,
- prepared);
- }
- SceneStatus directive_availability(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- std::uint32_t nameHash,
- std::int32_t elementIndex) noexcept {
- PreparedScene prepared{};
- return prepare_directive(view, occurrenceRow, slotRow, nameHash, elementIndex, prepared);
- }
- /** Sets one HUD directive element's state and visibility on a prepared objective slot. */
- SceneStatus set_directive(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- std::uint32_t nameHash,
- std::int32_t elementIndex,
- std::int8_t state,
- bool visible) noexcept {
- PreparedScene prepared{};
- const SceneStatus status =
- prepare_directive(view, occurrenceRow, slotRow, nameHash, elementIndex, prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- middleware::bap::activity_message::scriptable_auth::Type68Preset preset{
- .nameHash = nameHash, .elementIndex = elementIndex, .state = state, .visible = visible};
- std::array<std::byte, middleware::bap::activity_message::scriptable_auth::kType68ByteCount>
- body{};
- std::size_t written = 0;
- if (!middleware::bap::activity_message::scriptable_auth::encode_type68(preset, body, written)
- || written != body.size()) {
- return SceneStatus::invalidSlot;
- }
- return server::bap::request_activity_sdk_auth_override(
- view.binding,
- prepared.target,
- &prepared.rosterGroup,
- body,
- middleware::bap::activity_message::scriptable_auth::kType68BitCount,
- prepared.effectiveRegion,
- prepared.activityClientGeneration)
- ? SceneStatus::queued
- : SceneStatus::refused;
- }
- /**
- * Queues one authored dialogue cue against a reservation a script already holds.
- * @param reservation Output slot the caller reserved for this revision.
- * @param filterSlotRow Type-60 volume the line waits for, or none to play at once.
- * @return `queued` once the cue is staged, or the refusal that stopped it.
- */
- [[nodiscard]] SceneStatus
- play_dialogue_cue_reserved(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- std::uint16_t cueIndex,
- const host::ScriptableOutputReservation& reservation,
- std::optional<std::uint32_t> filterSlotRow) noexcept {
- PreparedScene prepared{};
- std::uint16_t authoredCueCount = 0;
- const SceneStatus status =
- prepare_dialogue(view, occurrenceRow, slotRow, cueIndex, prepared, authoredCueCount);
- if (status != SceneStatus::ready) {
- return status;
- }
- auth::Type2LaneClientRef filter{};
- if (filterSlotRow.has_value()) {
- const auto slots = view.catalog->slots();
- const auto objects = view.catalog->objects();
- if (*filterSlotRow >= slots.size()) {
- return SceneStatus::invalidSlot;
- }
- const sdk::format::Slot& volume = slots[*filterSlotRow];
- if (volume.slotType != static_cast<std::uint32_t>(auth::kType53FilterSlotType)
- || volume.objectIndex >= objects.size()
- || volume.slotIndex
- > static_cast<std::uint32_t>((std::numeric_limits<std::int16_t>::max)())
- || objects[volume.objectIndex].objectKey == 0) {
- return SceneStatus::invalidSlot;
- }
- filter = {objects[volume.objectIndex].objectKey,
- auth::kType53FilterSlotType,
- static_cast<std::int16_t>(volume.slotIndex)};
- }
- return server::bap::request_activity_state_local_dialogue_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- cueIndex,
- authoredCueCount,
- prepared.effectiveRegion,
- prepared.activityClientGeneration,
- &reservation,
- filter)
- ? SceneStatus::queued
- : SceneStatus::refused;
- }
- /** Checks one exact SDK-linked authored task. */
- SceneStatus task_availability(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- return prepare_task(view, occurrenceRow, slotRow, prepared);
- }
- SceneStatus objective_reset_availability(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- return prepare_objective(view, occurrenceRow, slotRow, prepared);
- }
- /** Clears every objective element of one prepared objective slot. */
- SceneStatus reset_objectives(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_objective(view, occurrenceRow, slotRow, prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- if (server::bap::request_activity_state_local_objective_reset(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- prepared.effectiveRegion,
- prepared.activityClientGeneration)) {
- return SceneStatus::queued;
- }
- return SceneStatus::refused;
- }
- /** Queues one exact objective reset using a caller-owned output reservation. */
- [[nodiscard]] SceneStatus
- reset_objectives_reserved(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- const host::ScriptableOutputReservation& reservation) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_objective(view, occurrenceRow, slotRow, prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- return server::bap::request_activity_state_local_objective_reset(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- prepared.effectiveRegion,
- prepared.activityClientGeneration,
- &reservation)
- ? SceneStatus::queued
- : SceneStatus::refused;
- }
- /** Queues the next generation through the dedicated type-38 encoder. */
- SceneStatus activate_task(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_task(view, occurrenceRow, slotRow, prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- if (server::bap::request_activity_state_local_task_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- prepared.effectiveRegion,
- prepared.activityClientGeneration)) {
- return SceneStatus::queued;
- }
- return SceneStatus::refused;
- }
- /**
- * Activates one authored task against a reservation a script already holds.
- * @param reservation Output slot the caller reserved for this revision.
- * @return `queued` once the task override is staged, or the refusal that stopped it.
- */
- [[nodiscard]] SceneStatus
- activate_task_reserved(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- const host::ScriptableOutputReservation& reservation) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_task(view, occurrenceRow, slotRow, prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- return server::bap::request_activity_state_local_task_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- prepared.effectiveRegion,
- prepared.activityClientGeneration,
- &reservation)
- ? SceneStatus::queued
- : SceneStatus::refused;
- }
- /** @return Whether one occurrence's sequence slot can be played right now. */
- SceneStatus sequence_availability(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- return prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kSequenceSlotType,
- sdk::format::kSequenceComponentClass,
- sdk::format::kSequenceAuthSchema,
- false,
- prepared);
- }
- /** Plays one sequence slot of a prepared behavior occurrence. */
- SceneStatus play_sequence(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kSequenceSlotType,
- sdk::format::kSequenceComponentClass,
- sdk::format::kSequenceAuthSchema,
- false,
- prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- if (server::bap::request_activity_state_local_sequence_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- prepared.effectiveRegion,
- prepared.activityClientGeneration)) {
- return SceneStatus::queued;
- }
- return SceneStatus::refused;
- }
- /** @return Whether one occurrence's cinematic slot can be driven right now. */
- SceneStatus cinematic_availability(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow) noexcept {
- PreparedScene prepared{};
- return prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kCinematicSlotType,
- sdk::format::kCinematicComponentClass,
- sdk::format::kCinematicAuthSchema,
- false,
- prepared);
- }
- /** Sets one cinematic slot active or inactive on a prepared behavior occurrence. */
- SceneStatus set_cinematic_active(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- bool active) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kCinematicSlotType,
- sdk::format::kCinematicComponentClass,
- sdk::format::kCinematicAuthSchema,
- false,
- prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- if (server::bap::request_activity_state_local_cinematic_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- active,
- prepared.effectiveRegion,
- prepared.activityClientGeneration)) {
- return SceneStatus::queued;
- }
- return SceneStatus::refused;
- }
- /** Plays one sequence slot against an already-reserved Host output revision. */
- SceneStatus play_sequence_reserved(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- const host::ScriptableOutputReservation& reservation) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kSequenceSlotType,
- sdk::format::kSequenceComponentClass,
- sdk::format::kSequenceAuthSchema,
- false,
- prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- return server::bap::request_activity_state_local_sequence_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- prepared.effectiveRegion,
- prepared.activityClientGeneration,
- &reservation)
- ? SceneStatus::queued
- : SceneStatus::refused;
- }
- /**
- * Drives one cinematic behavior against a reservation a script already holds.
- * @param reservation Output slot the caller reserved for this revision.
- * @return `queued` once the override is staged, or the refusal that stopped it.
- */
- SceneStatus
- set_cinematic_active_reserved(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- bool active,
- const host::ScriptableOutputReservation& reservation) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kCinematicSlotType,
- sdk::format::kCinematicComponentClass,
- sdk::format::kCinematicAuthSchema,
- false,
- prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- return server::bap::request_activity_state_local_cinematic_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- active,
- prepared.effectiveRegion,
- prepared.activityClientGeneration,
- &reservation)
- ? SceneStatus::queued
- : SceneStatus::refused;
- }
- /** Finds the occurrence a slot currently belongs to. @return `invalidView` on a stale view. */
- [[nodiscard]] static SceneStatus current_behavior_occurrence(
- const sdk::BoundView& view, std::uint32_t slotRow, std::uint32_t& occurrenceRow) noexcept {
- occurrenceRow = sdk::format::kAbsentIndex;
- Snapshot snapshot{};
- if (query(view, snapshot) != Status::ready || view.catalog == nullptr) {
- return SceneStatus::invalidView;
- }
- const auto slots = view.catalog->slots();
- const auto occurrences = view.catalog->occurrences();
- if (slotRow >= slots.size()) {
- return SceneStatus::invalidSlot;
- }
- server::bap::ActivityLinkView link{};
- const SceneStatus live = scene_binding_status(view, link);
- if (live != SceneStatus::ready) {
- return live;
- }
- const auto selected = behavior_scope::select(occurrences,
- view.catalog->states(),
- view.catalog->bubbles(),
- view.scenarioRow,
- slots[slotRow].objectIndex,
- snapshot.plan.stateRow,
- link.effectiveRegion);
- if (selected.ambiguous) {
- return SceneStatus::ambiguousTarget;
- }
- occurrenceRow = selected.row;
- return occurrenceRow == sdk::format::kAbsentIndex ? SceneStatus::targetUnavailable
- : SceneStatus::ready;
- }
- SceneStatus sequence_slot_availability(const sdk::BoundView& view, std::uint32_t slotRow) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready ? sequence_availability(view, occurrenceRow, slotRow)
- : found;
- }
- SceneStatus objective_reset_slot_availability(const sdk::BoundView& view,
- std::uint32_t slotRow) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready ? objective_reset_availability(view, occurrenceRow, slotRow)
- : found;
- }
- SceneStatus
- reset_objectives_slot_reserved(const sdk::BoundView& view,
- std::uint32_t slotRow,
- const host::ScriptableOutputReservation& reservation) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready
- ? reset_objectives_reserved(view, occurrenceRow, slotRow, reservation)
- : found;
- }
- SceneStatus
- play_sequence_slot_reserved(const sdk::BoundView& view,
- std::uint32_t slotRow,
- const host::ScriptableOutputReservation& reservation) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready
- ? play_sequence_reserved(view, occurrenceRow, slotRow, reservation)
- : found;
- }
- SceneStatus cinematic_slot_availability(const sdk::BoundView& view,
- std::uint32_t slotRow) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready ? cinematic_availability(view, occurrenceRow, slotRow)
- : found;
- }
- /**
- * Resolves the slot's current occurrence, then drives its cinematic behavior.
- * @param reservation Output slot the caller reserved for this revision.
- * @return `queued` once the override is staged, or the refusal that stopped it.
- */
- SceneStatus
- set_cinematic_slot_active_reserved(const sdk::BoundView& view,
- std::uint32_t slotRow,
- bool active,
- const host::ScriptableOutputReservation& reservation) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready
- ? set_cinematic_active_reserved(view, occurrenceRow, slotRow, active, reservation)
- : found;
- }
- /** Starts one named state of the actor a type-42 sensor drives, behind its rising generation. */
- [[nodiscard]] static SceneStatus
- play_performance_reserved(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- std::uint32_t stateNameHash,
- const host::ScriptableOutputReservation& reservation) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kPerformanceSlotType,
- sdk::format::kPerformanceComponentClass,
- sdk::format::kPerformanceAuthSchema,
- false,
- prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- return server::bap::request_activity_state_local_performance_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- stateNameHash,
- prepared.effectiveRegion,
- prepared.activityClientGeneration,
- &reservation)
- ? SceneStatus::queued
- : SceneStatus::refused;
- }
- /** Starts one state on the squad the sensor drives, through the slot's current occurrence. */
- SceneStatus
- play_performance_slot_reserved(const sdk::BoundView& view,
- std::uint32_t slotRow,
- std::uint32_t stateNameHash,
- const host::ScriptableOutputReservation& reservation) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready
- ? play_performance_reserved(view, occurrenceRow, slotRow, stateNameHash, reservation)
- : found;
- }
- /** Starts one authored state on the squad a type-42 sensor drives, for an operator action. */
- SceneStatus play_performance_slot(const sdk::BoundView& view,
- std::uint32_t slotRow,
- std::uint32_t stateNameHash) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- if (found != SceneStatus::ready) {
- return found;
- }
- PreparedScene prepared{};
- const SceneStatus status = prepare_typed_behavior(view,
- occurrenceRow,
- slotRow,
- sdk::format::kPerformanceSlotType,
- sdk::format::kPerformanceComponentClass,
- sdk::format::kPerformanceAuthSchema,
- false,
- prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- return server::bap::request_activity_state_local_performance_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- stateNameHash,
- prepared.effectiveRegion,
- prepared.activityClientGeneration)
- ? SceneStatus::queued
- : SceneStatus::refused;
- }
- SceneStatus task_slot_availability(const sdk::BoundView& view, std::uint32_t slotRow) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready ? task_availability(view, occurrenceRow, slotRow) : found;
- }
- SceneStatus
- activate_task_slot_reserved(const sdk::BoundView& view,
- std::uint32_t slotRow,
- const host::ScriptableOutputReservation& reservation) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready
- ? activate_task_reserved(view, occurrenceRow, slotRow, reservation)
- : found;
- }
- SceneStatus dialogue_cue_slot_availability(const sdk::BoundView& view,
- std::uint32_t slotRow,
- std::uint16_t cueIndex) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready
- ? dialogue_cue_availability(view, occurrenceRow, slotRow, cueIndex)
- : found;
- }
- /**
- * Resolves the slot's current occurrence, then queues its authored dialogue cue.
- * @param reservation Output slot the caller reserved for this revision.
- * @param filterSlotRow Type-60 volume the line waits for, or none to play at once.
- * @return `queued` once the cue is staged, or the refusal that stopped it.
- */
- SceneStatus play_dialogue_cue_slot_reserved(const sdk::BoundView& view,
- std::uint32_t slotRow,
- std::uint16_t cueIndex,
- const host::ScriptableOutputReservation& reservation,
- std::optional<std::uint32_t> filterSlotRow) noexcept {
- std::uint32_t occurrenceRow = 0;
- const SceneStatus found = current_behavior_occurrence(view, slotRow, occurrenceRow);
- return found == SceneStatus::ready
- ? play_dialogue_cue_reserved(
- view, occurrenceRow, slotRow, cueIndex, reservation, filterSlotRow)
- : found;
- }
- /** Queues one preflighted authored scene only through an exact unarmed Host revision. */
- SceneStatus activate_authored_scene_reserved(const sdk::BoundView& view,
- std::uint32_t occurrenceRow,
- std::uint32_t slotRow,
- const host::ScriptableOutputReservation& reservation,
- std::uint32_t eventKey,
- bool stop) noexcept {
- PreparedScene prepared{};
- const SceneStatus status = prepare_scene(view, occurrenceRow, slotRow, prepared);
- if (status != SceneStatus::ready) {
- return status;
- }
- if (prepared.omittedParticipants != 0) {
- log_omitted_participants(*view.catalog, slotRow, prepared.omittedParticipants);
- }
- if (server::bap::request_activity_state_local_authored_scene_override(
- view.binding,
- prepared.target,
- prepared.rosterGroup,
- prepared.effectiveRegion,
- prepared.activityClientGeneration,
- &reservation,
- prepared.sceneDependencies,
- eventKey,
- stop)) {
- return SceneStatus::queued;
- }
- return SceneStatus::refused;
- }
- /** Returns stable concise text for one mission runtime result. */
- const char* status_name(Status status) noexcept {
- switch (status) {
- case Status::ready:
- return "ready";
- case Status::invalidView:
- return "invalid_view";
- case Status::staleBinding:
- return "stale_binding";
- case Status::staleActivityClient:
- return "stale_activity_client";
- case Status::noActivityLink:
- return "no_activity_link";
- case Status::missingLiveSliceSet:
- return "missing_live_slice_set";
- case Status::wrongScenario:
- return "wrong_scenario";
- case Status::wrongSliceSet:
- return "wrong_slice_set";
- case Status::missingInitialState:
- return "missing_initial_state";
- case Status::ambiguousInitialState:
- return "ambiguous_initial_state";
- case Status::invalidOccurrence:
- return "invalid_occurrence";
- case Status::schemaJoinNotExact:
- return "schema_join_not_exact";
- case Status::invalidRosterGroup:
- return "invalid_roster_group";
- case Status::rosterKeyConflict:
- return "roster_key_conflict";
- case Status::groupCapacityExceeded:
- return "group_capacity_exceeded";
- case Status::outputBusy:
- return "output_busy";
- case Status::refused:
- return "refused";
- }
- return "refused";
- }
- /** Returns stable concise text for one authored-scene result. */
- const char* status_name(SceneStatus status) noexcept {
- switch (status) {
- case SceneStatus::ready:
- return "ready";
- case SceneStatus::queued:
- return "queued";
- case SceneStatus::invalidView:
- return "invalid_view";
- case SceneStatus::staleBinding:
- return "stale_binding";
- case SceneStatus::staleActivityClient:
- return "stale_activity_client";
- case SceneStatus::noActivityLink:
- return "no_activity_link";
- case SceneStatus::invalidOccurrence:
- return "invalid_occurrence";
- case SceneStatus::invalidSlot:
- return "invalid_slot";
- case SceneStatus::wrongScenario:
- return "wrong_scenario";
- case SceneStatus::wrongState:
- return "wrong_state";
- case SceneStatus::schemaJoinNotExact:
- return "schema_join_not_exact";
- case SceneStatus::missingResource:
- return "missing_resource";
- case SceneStatus::ambiguousResource:
- return "ambiguous_resource";
- case SceneStatus::targetUnavailable:
- return "target_unavailable";
- case SceneStatus::ambiguousTarget:
- return "ambiguous_target";
- case SceneStatus::missionSeedUnavailable:
- return "mission_seed_unavailable";
- case SceneStatus::missionSeedPending:
- return "mission_seed_pending";
- case SceneStatus::outputBusy:
- return "output_busy";
- case SceneStatus::dependencyCapacity:
- return "dependency_capacity";
- case SceneStatus::refused:
- return "refused";
- }
- return "refused";
- }
- } // namespace sunrise::server::activity::activity_sdk_mission
|