Safe Haskell | Safe-Inferred |
---|
Synopsis
- class Cacheable d where
- from_cache_entry :: CacheEntry -> Maybe.Maybe (CallType d)
- to_cache_entry :: CallType d -> CacheEntry
- block :: BlockId -> (PassedArgs d -> NoteDeriver) -> PassedArgs d -> NoteDeriver
- track :: Cacheable d => TrackTree.Track -> Set TrackId -> Deriver (Stream.Stream d) -> Deriver (Stream.Stream d)
- get_control_damage :: BlockId -> TrackId -> (ScoreTime, ScoreTime) -> Deriver ControlDamage
- get_tempo_damage :: BlockId -> TrackId -> TrackTime -> Events.Events -> Deriver ControlDamage
- is_cache_log :: Log.Msg -> Bool
- cache_hit_events :: Log.Msg -> Maybe.Maybe Int
- cache_miss_reason :: Log.Msg -> Maybe.Maybe Text
- pretty_cache :: Cache -> Text
Documentation
class Cacheable d where Source #
from_cache_entry :: CacheEntry -> Maybe.Maybe (CallType d) Source #
to_cache_entry :: CallType d -> CacheEntry Source #
Instances
Cacheable PSignal Source # | |
Defined in Derive.Cache | |
Cacheable Score.Event Source # | |
Defined in Derive.Cache | |
Cacheable Signal.Control Source # | |
Defined in Derive.Cache |
block :: BlockId -> (PassedArgs d -> NoteDeriver) -> PassedArgs d -> NoteDeriver Source #
If the given generator has a cache entry, relevant derivation context is the same as the cache entry's, and there is no damage under the generator, I can reuse the cached values for it. This is effectively a kind of memoization. If the generator is called, the results will be put in the cache before being returned.
:: Cacheable d | |
=> TrackTree.Track | |
-> Set TrackId | Children, as documented in |
-> Deriver (Stream.Stream d) | |
-> Deriver (Stream.Stream d) |
Cache a track, but only if it's not sliced and has a TrackId.
:: BlockId | |
-> TrackId | |
-> (ScoreTime, ScoreTime) | track_range must be passed explicitly because the event may have been sliced and shifted, but ControlDamage should be relative to the start of the track at ScoreTime 0. |
-> Deriver ControlDamage |
ScoreDamage on the current track is converted into ControlDamage, and expanded to the neighbor events. This is because control calls emit samples between their previous or next events. Then this is merged with any ControlDamage inherited from callers.
If a block call is touched by control damage, the the control damage expands to cover the entire block.
Previously, this inherited damage would also be expanded to its neighbor events, under the rationale that controls can modify other controls. While this is true, it causes an annoying situation where a control track with a single call under (say) a tempo track will cause any edits to the tempo track to invalidate the entire score. This happens a lot in practice, and I've forgotten about this wrinkle a number of times
The downside, of course, is that control damage will not cause a control call that lies before its previous event to rederive, even if it should have. I'll have to see how annoying this is in practice.
get_tempo_damage :: BlockId -> TrackId -> TrackTime -> Events.Events -> Deriver ControlDamage Source #
Since the warp is the integral of the tempo track, damage on the tempo track will affect all events after it. Actually, the damage extends from the previous event to the end of the track, since interpolating calls extend from the previous event.
It would be simpler to have any edit invalidate the whole track, but it seems like editing a score at the end is a common case, and it would be a shame to rederive the entire score on each edit when only the very end has changed.
is_cache_log :: Log.Msg -> Bool Source #
cache_hit_events :: Log.Msg -> Maybe.Maybe Int Source #
Get the number of cached events from a cache_hit_msg
.
cache_miss_reason :: Log.Msg -> Maybe.Maybe Text Source #
Get the reason from a cache_miss_msg
.
debugging
pretty_cache :: Cache -> Text Source #
Format the cache in a hopefully readable way.