Class UpdatableSongSession

java.lang.Object
org.jjazz.musiccontrol.api.playbacksession.UpdatableSongSession
All Implemented Interfaces:
PropertyChangeListener, EventListener, ControlTrackProvider, EndOfPlaybackActionProvider, PlaybackSession, SongContextProvider
Direct Known Subclasses:
UpdatableSongSessionOnePlay

An UpdatableSongSession is a BaseSongSession wrapper which enables on-the-fly updates of the playing sequence using updateSequence(org.jjazz.musiccontrol.api.playbacksession.UpdatableSongSession.Update).

Authorized udpates are notes+control track changes which do not change the Sequence size. Only user phrase modification or removal is supported.

The class uses buffer tracks and mute/unmute tracks to enable on-the-fly sequence changes.

If the BaseSongSession is an instance of UpdateProvider, the UpdatableSongSession listens to updates availability and automatically apply the updates.

  • Field Details

  • Method Details

    • getSession

      public static UpdatableSongSession getSession(BaseSongSession session)
      Create or reuse a session for the specified parameters.

      Sessions are cached: if an existing session already exists for the same parameters then return it, otherwise a new session is created.

      Parameters:
      session - Must be in the NEW or GENERATED state. If it is an UpdateProvider instance automatically apply the updates when available.
      Returns:
    • getBaseSession

      public BaseSongSession getBaseSession()
    • getFreshCopy

      public UpdatableSongSession getFreshCopy(SongContext sgContext)
      Description copied from interface: PlaybackSession
      Get a copy of this session in the NEW state for the specified context.
      Specified by:
      getFreshCopy in interface PlaybackSession
      Parameters:
      sgContext - If null use a copy of this session'SongContext
      Returns:
    • generate

      public void generate(boolean silent) throws MusicGenerationException
      Description copied from interface: PlaybackSession
      Create the sequence and the related data.

      If generation is successful the method changes the state from NEW to GENERATED.

      Specified by:
      generate in interface PlaybackSession
      Parameters:
      silent - If false a modal progress bar is shown why generating the music.
      Throws:
      MusicGenerationException
    • getSequence

      public Sequence getSequence()
      Get the sequence which contains the original song tracks plus additional empty tracks to allow "double buffering modification" via muting/unmuting tracks.

      The total number of tracks is 2 * getNbPlayingTracks().

      Specified by:
      getSequence in interface PlaybackSession
      Returns:
    • getNbPlayingTracks

      public int getNbPlayingTracks()
      The number of playing tracks (excluding the additional double buffering extra tracks).
      Returns:
    • getOriginalSequenceSize

      public long getOriginalSequenceSize()
      The size in ticks of the original generated sequence.
      Returns:
    • isEnabled

      public boolean isEnabled()
      Check is this session is enabled.

      The session is enabled by default upon creation. It might be automatically disabled when our base song session is an UpdateProvider which can not provide updates anymore.

      Returns:
    • setEnabled

      public void setEnabled(boolean b)
      Disable the session: session will ignore received updates.
      Parameters:
      b -
      See Also:
    • updateSequence

      public void updateSequence(UpdatableSongSession.Update update)
      Update the sequence with the specified parameter.

      Update RhythmVoice tracks for which there is an actual change. Changes are first applied to muted "buffer tracks", then we switch the mute status between the buffer and the playing tracks. The transition might be noticeable if notes were still ringing when tracks mute state is switched.

      Fire a PROP_UPDATED_RECEIVED change event.

      The method does nothing if session is disabled.

      Parameters:
      update -
      Throws:
      IllegalArgumentException - If a MidiEvent tick position is beyond getOriginalSequenceSize(), or if session is not in the GENERATED state.
    • getOriginalRvTrackIdMap

      public Map<RhythmVoice,Integer> getOriginalRvTrackIdMap()
      A map providing the original track id corresponding to each used RhythmVoice in the given context.

      If a song uses rhythms R1 and R2 and context is only on R2 bars, then the map only contains R2 rhythm voices and track id.

      Returns:
      See Also:
      • getOriginalTrackEvents()
    • getOriginalRvPhraseMap

      public Map<RhythmVoice,Phrase> getOriginalRvPhraseMap()
      A map giving the original resulting Phrase for each RhythmVoice, in the current context.

      Returns:
    • getCurrentRvPhraseMap

      public Map<RhythmVoice,Phrase> getCurrentRvPhraseMap()
      Get the current Phrase for each RhythmVoice track.
      Returns:
    • getState

      public PlaybackSession.State getState()
      Description copied from interface: PlaybackSession
      Get the state of this session.
      Specified by:
      getState in interface PlaybackSession
      Returns:
      See Also:
    • isDirty

      public boolean isDirty()
      Description copied from interface: PlaybackSession
      Return true if the sequence is not up-to-date with its underlying data.

      If playback is stopped a new session should be created.

      Specified by:
      isDirty in interface PlaybackSession
      Returns:
      See Also:
    • getTempo

      public int getTempo()
      Description copied from interface: PlaybackSession
      Get the tempo in BPM.
      Specified by:
      getTempo in interface PlaybackSession
      Returns:
      -1 if no meaningful value can be returned.
      See Also:
    • getTracksMuteStatus

      public HashMap<Integer,Boolean> getTracksMuteStatus()
      Description copied from interface: PlaybackSession
      Get the mute status of each track id.

      Note that track 0 (e.g. mandatory track for sequence name, tempo and time signature changes, etc.) is not included.

      Specified by:
      getTracksMuteStatus in interface PlaybackSession
      Returns:
      Key=track id, Value=true if track is muted. Can be null if no meaningful value can be returned.
      See Also:
    • getLoopEndTick

      public long getLoopEndTick()
      Description copied from interface: PlaybackSession
      The tick position of the end of the loop.

      Specified by:
      getLoopEndTick in interface PlaybackSession
      Returns:
      -1 if no meaningful value can be returned (loop will be at the end of sequence)
    • getLoopStartTick

      public long getLoopStartTick()
      Description copied from interface: PlaybackSession
      The tick position of the start of the loop.

      Specified by:
      getLoopStartTick in interface PlaybackSession
      Returns:
      -1 if no meaningful value can be returned.
    • getLoopCount

      public int getLoopCount()
      Description copied from interface: PlaybackSession
      The sequencer loop count (see Java Sequencer setLoopCount()).
      Specified by:
      getLoopCount in interface PlaybackSession
      Returns:
      0 means sequence is played only once, 1 means sequence is played twice, etc. -1 means loop forever.
    • getBarRange

      public IntRange getBarRange()
      Description copied from interface: PlaybackSession
      The bar range corresponding to the sequence.
      Specified by:
      getBarRange in interface PlaybackSession
      Returns:
      Null if no meaningful value can be returned.
    • getTick

      public long getTick(int barIndex)
      Description copied from interface: PlaybackSession
      Get the start tick position corresponding to the specified bar.
      Specified by:
      getTick in interface PlaybackSession
      Returns:
      -1 if no meaningful value can be returned.
    • close

      public void close()
      Description copied from interface: PlaybackSession
      Put session in the CLOSED state and release used resources, so that session can be disposed.
      Specified by:
      close in interface PlaybackSession
      See Also:
    • addPropertyChangeListener

      public void addPropertyChangeListener(PropertyChangeListener l)
      Specified by:
      addPropertyChangeListener in interface PlaybackSession
    • removePropertyChangeListener

      public void removePropertyChangeListener(PropertyChangeListener l)
      Specified by:
      removePropertyChangeListener in interface PlaybackSession
    • equals

      public boolean equals(Object obj)
      Overridden to do the equals only on the underlying BaseSongSession.
      Overrides:
      equals in class Object
      Parameters:
      obj -
      Returns:
    • hashCode

      public int hashCode()
      Overridden to do the hash only on the underlying BaseSongSession.
      Overrides:
      hashCode in class Object
      Returns:
    • getSongContext

      public SongContext getSongContext()
      Specified by:
      getSongContext in interface SongContextProvider
    • getControlTrack

      public ControlTrack getControlTrack()
      Description copied from interface: ControlTrackProvider
      get the control track.
      Specified by:
      getControlTrack in interface ControlTrackProvider
      Returns:
      Null if no contral track available.
    • getEndOfPlaybackAction

      public ActionListener getEndOfPlaybackAction()
      Description copied from interface: EndOfPlaybackActionProvider
      An action to be executed when music playback is stopped or paused (because user stopped it or end of sequence is reached).
      Specified by:
      getEndOfPlaybackAction in interface EndOfPlaybackActionProvider
      Returns:
      Can be null
    • propertyChange

      public void propertyChange(PropertyChangeEvent e)
      Specified by:
      propertyChange in interface PropertyChangeListener
    • toString

      public String toString()
      Overrides:
      toString in class Object