MayaFlux 1.0.0
Digital-First Multimedia Processing Framework
Loading...
Searching...
No Matches
Locus.hpp
Go to the documentation of this file.
1#pragma once
2
3#include "Agent.hpp"
4
6
7namespace MayaFlux::Buffers {
8class RenderProcessor;
9}
10
11namespace MayaFlux::Nexus {
12
13/**
14 * @class Locus
15 * @brief Agent that perceives the world from a navigation state and influences
16 * how the things it touches are viewed.
17 *
18 * An Agent already carries both a perception function and an influence
19 * function. Locus makes both concrete around a Kinesis::NavigationState:
20 *
21 * Perception is observation. The navigation state is the lens. Held movement
22 * flags, yaw, and pitch advance the eye; the perception path integrates that
23 * motion against elapsed time and produces the current ViewTransform. The
24 * Locus sees the world from wherever its navigation state currently sits, and
25 * its inherited Agent position follows the eye so the spatial index and any
26 * PerceptionContext observe the same point.
27 *
28 * Influence is re-viewing. A Locus holds a set of view targets: render
29 * processors whose view transform it drives. On each influence the current
30 * ViewTransform is pushed to every target. The same motion that determines
31 * what the Locus perceives determines how everything under its influence is
32 * seen. Multiple processors driven by one Locus share its viewpoint; multiple
33 * Loci over disjoint targets partition the scene into independently-viewed
34 * regions.
35 *
36 * The base perception and influence callables still fire. Locus layers its view
37 * behaviour on top: the user callables run, then the view is integrated and
38 * distributed. A user perception callable can read the freshly produced
39 * transform through the Locus; a user influence callable can add domain effects
40 * alongside the view push.
41 *
42 * The navigation state is plain data, mutated directly through nav() or via the
43 * Kinesis free functions (apply_mouse_delta, apply_scroll, snap_ortho). Wiring a
44 * Locus with every(1.0/60.0) drives the whole cycle each frame. Because the view
45 * push writes a render processor UBO, wire the Locus so its influence fires on
46 * the graphics thread when it drives view targets.
47 */
48class MAYAFLUX_API Locus : public Agent {
49public:
50 /**
51 * @brief Construct from a NavigationConfig with perception and influence functions.
52 * @param config Initial navigation configuration. eye seeds the position.
53 * @param query_radius Radius passed to the spatial index on each commit.
54 * @param perception User perception callable, fired before the view integrates.
55 * @param influence User influence callable, fired before the view is pushed.
56 */
57 Locus(const Kinesis::NavigationConfig& config,
58 float query_radius,
59 PerceptionFn perception,
60 InfluenceFn influence);
61
62 /**
63 * @brief Construct from a NavigationConfig with named perception and influence functions.
64 * @param config Initial navigation configuration. eye seeds the position.
65 * @param query_radius Radius passed to the spatial index on each commit.
66 * @param perception_fn_name Identifier for the perception function.
67 * @param perception User perception callable, fired before the view integrates.
68 * @param influence_fn_name Identifier for the influence function.
69 * @param influence User influence callable, fired before the view is pushed.
70 */
71 Locus(const Kinesis::NavigationConfig& config,
72 float query_radius,
73 std::string perception_fn_name, PerceptionFn perception,
74 std::string influence_fn_name, InfluenceFn influence);
75
76 // =========================================================================
77 // Navigation state
78 // =========================================================================
79
80 /**
81 * @brief Mutable access to the navigation lens.
82 *
83 * Movement flags, yaw, pitch, and tuning fields are mutated through this
84 * reference or via the Kinesis free functions. The eye advances on the next
85 * perceive(); the inherited position follows.
86 */
87 [[nodiscard]] Kinesis::NavigationState& nav() { return m_nav; }
88
89 /**
90 * @brief Read-only access to the navigation lens.
91 */
92 [[nodiscard]] const Kinesis::NavigationState& nav() const { return m_nav; }
93
94 /**
95 * @brief The ViewTransform produced by the most recent perceive().
96 *
97 * Valid after the first commit-driven or wired invocation. Before that it
98 * is the transform of the initial navigation state at unit aspect.
99 */
100 [[nodiscard]] const Kinesis::ViewTransform& current_view() const { return m_view; }
101
102 /**
103 * @brief Aspect ratio used when integrating the view.
104 *
105 * Defaults to 1. Set from the target window's framebuffer dimensions so the
106 * projection matches what is on screen.
107 */
108 void set_aspect(float aspect) { m_aspect = aspect; }
109
110 /** @brief Current aspect ratio. */
111 [[nodiscard]] float aspect() const { return m_aspect; }
112
113 // =========================================================================
114 // View targets — the processors this Locus re-views
115 // =========================================================================
116
117 /**
118 * @brief Add a render processor whose view transform this Locus drives.
119 *
120 * On each influence the processor receives the Locus's current
121 * ViewTransform. Adding the same processor twice is a no-op. The processor
122 * must outlive the Locus or be removed via remove_view_target().
123 *
124 * @param proc Render processor to drive. Ignored if null.
125 */
126 void add_view_target(std::shared_ptr<Buffers::RenderProcessor> proc);
127
128 /**
129 * @brief Stop driving a render processor's view transform.
130 * @param proc Processor previously added via add_view_target().
131 */
132 void remove_view_target(const std::shared_ptr<Buffers::RenderProcessor>& proc);
133
134 /**
135 * @brief All render processors currently driven by this Locus.
136 */
137 [[nodiscard]] const std::vector<std::shared_ptr<Buffers::RenderProcessor>>& view_targets() const
138 {
139 return m_view_targets;
140 }
141
142 // =========================================================================
143 // Perception and influence — Locus behaviour layered on the Agent path
144 // =========================================================================
145
146 /**
147 * @brief Perceive: run the user perception callable, then integrate the view.
148 *
149 * Fires the inherited perception callable with @p ctx, advances the eye by
150 * held movement flags scaled by elapsed time, mirrors the new eye into the
151 * inherited position, and stores the resulting ViewTransform. The Locus
152 * now sees the world from its updated state.
153 *
154 * @param ctx Perception context built by Fabric from the spatial snapshot.
155 */
156 void invoke_perception(const PerceptionContext& ctx) override;
157
158 /**
159 * @brief Influence: push the current view to every view target, then run
160 * the inherited influence path.
161 *
162 * Sets the stored ViewTransform on each render processor in
163 * view_targets(), then fires the inherited influence callable with @p ctx
164 * and dispatches the Locus's audio and render sinks and its attachment.
165 * Everything under this Locus's influence is seen from its viewpoint, and an
166 * attached buffer that is also a view target is placed over the fresh view.
167 *
168 * @param ctx Influence context built by Fabric from the Locus's state.
169 */
170 void invoke_influence(const InfluenceContext& ctx) const override;
171
172private:
175 float m_aspect { 1.0F };
176 std::vector<std::shared_ptr<Buffers::RenderProcessor>> m_view_targets;
177};
178
179} // namespace MayaFlux::Nexus
float query_radius
Definition Decoder.cpp:96
std::function< void(const PerceptionContext &)> PerceptionFn
Definition Agent.hpp:39
std::function< void(const InfluenceContext &)> InfluenceFn
Definition Agent.hpp:38
Object that both perceives nearby entities and acts on MayaFlux objects.
Definition Agent.hpp:36
const Kinesis::ViewTransform & current_view() const
The ViewTransform produced by the most recent perceive().
Definition Locus.hpp:100
Kinesis::NavigationState m_nav
Definition Locus.hpp:173
const std::vector< std::shared_ptr< Buffers::RenderProcessor > > & view_targets() const
All render processors currently driven by this Locus.
Definition Locus.hpp:137
const Kinesis::NavigationState & nav() const
Read-only access to the navigation lens.
Definition Locus.hpp:92
std::vector< std::shared_ptr< Buffers::RenderProcessor > > m_view_targets
Definition Locus.hpp:176
void set_aspect(float aspect)
Aspect ratio used when integrating the view.
Definition Locus.hpp:108
float aspect() const
Current aspect ratio.
Definition Locus.hpp:111
Kinesis::NavigationState & nav()
Mutable access to the navigation lens.
Definition Locus.hpp:87
Agent that perceives the world from a navigation state and influences how the things it touches are v...
Definition Locus.hpp:48
Tuning parameters for a first-person fly-navigation controller.
Mutable first-person navigation state.
View and projection matrices as a named push constant slot.
Data passed to an Emitter or Agent influence function on each commit.
Definition Influence.hpp:17
Data passed to a Sensor or Agent perception function on each commit.