Browse Source

Remove old code that did apparently nothing than crash. Regressions here we come :)

master
Nils 4 years ago
parent
commit
f559adf181
  1. 90
      engine/api.py
  2. 83
      engine/pattern.py
  3. 10
      qtgui/mainwindow.py
  4. 11
      qtgui/pattern_grid.py

90
engine/api.py

@ -54,16 +54,16 @@ class ClientCallbacks(Callbacks): #inherits from the templates api callbacks
ppqn = cbox.Transport.status().pos_ppqn * session.data.subdivisions ppqn = cbox.Transport.status().pos_ppqn * session.data.subdivisions
status = playbackStatus() status = playbackStatus()
for func in self.setPlaybackTicks: for func in self.setPlaybackTicks:
func(ppqn, status) func(ppqn, status)
def _loopChanged(self, measurenumber, loopStart, loopEnd): def _loopChanged(self, measurenumber, loopStart, loopEnd):
export = measurenumber export = measurenumber
for func in self.loopChanged: for func in self.loopChanged:
func(export) func(export)
def _timeSignatureChanged(self): def _timeSignatureChanged(self):
nr = session.data.howManyUnits nr = session.data.howManyUnits
typ = session.data.whatTypeOfUnit typ = session.data.whatTypeOfUnit
for func in self.timeSignatureChanged: for func in self.timeSignatureChanged:
func(nr, typ) func(nr, typ)
@ -79,26 +79,26 @@ class ClientCallbacks(Callbacks): #inherits from the templates api callbacks
You don't need to redraw anything if you don't want to. One recommendation is to You don't need to redraw anything if you don't want to. One recommendation is to
draw every n step a little more important (bigger, different color). draw every n step a little more important (bigger, different color).
where n = subdivions where n = subdivions
We also place JACK BBT via tempoMap here because we need it every time the time sig We also place JACK BBT via tempoMap here because we need it every time the time sig
changes (which calls _subdivisionsChanged) and if subdivisions change. changes (which calls _subdivisionsChanged) and if subdivisions change.
""" """
typ = baseDurationToTraditionalNumber[session.data.whatTypeOfUnit] typ = baseDurationToTraditionalNumber[session.data.whatTypeOfUnit]
nr = session.data.howManyUnits nr = session.data.howManyUnits
tradNr = int(nr / session.data.subdivisions) tradNr = int(nr / session.data.subdivisions)
#JACK BBT for Timebase Master. No matter if we are master at the moment or not. #JACK BBT for Timebase Master. No matter if we are master at the moment or not.
if tradNr == nr / session.data.subdivisions: if tradNr == nr / session.data.subdivisions:
#Easier to read than the else case. Not possible with 9 Steps per Pattern in Groups of 2 because that is a 4.5/4 timesig. #Easier to read than the else case. Not possible with 9 Steps per Pattern in Groups of 2 because that is a 4.5/4 timesig.
session.data.tempoMap.setTimeSignature(tradNr, typ) session.data.tempoMap.setTimeSignature(tradNr, typ)
else: else:
#Always possible, compared to first if case. #Always possible, compared to first if case.
session.data.tempoMap.setTimeSignature(nr, typ*session.data.subdivisions) session.data.tempoMap.setTimeSignature(nr, typ*session.data.subdivisions)
export = session.data.subdivisions export = session.data.subdivisions
for func in self.subdivisionsChanged: for func in self.subdivisionsChanged:
func(export) func(export)
callbacks._dataChanged() callbacks._dataChanged()
def _scoreChanged(self): def _scoreChanged(self):
"""This includes the time signature as well, but is not send on a timesig change. """This includes the time signature as well, but is not send on a timesig change.
@ -120,7 +120,7 @@ class ClientCallbacks(Callbacks): #inherits from the templates api callbacks
and stepChanged.""" and stepChanged."""
export = track.export() export = track.export()
for func in self.exportCacheChanged: for func in self.exportCacheChanged:
func(export) func(export)
def _patternChanged(self, track): def _patternChanged(self, track):
"""each track has only one pattern. We can identify the pattern by track and vice versa. """each track has only one pattern. We can identify the pattern by track and vice versa.
@ -163,7 +163,7 @@ class ClientCallbacks(Callbacks): #inherits from the templates api callbacks
def _trackMetaDataChanged(self, track): def _trackMetaDataChanged(self, track):
"""a low cost function that should not trigger anything costly to redraw """a low cost function that should not trigger anything costly to redraw
but some text and simple widgets.""" but some text and simple widgets."""
export = track.export() export = track.export()
for func in self.trackMetaDataChanged: for func in self.trackMetaDataChanged:
func(export) func(export)
callbacks._dataChanged() callbacks._dataChanged()
@ -182,7 +182,7 @@ from template.engine.api import callbacks
_templateStartEngine = startEngine _templateStartEngine = startEngine
def updatePlayback(): def updatePlayback():
#TODO: use template.sequencer.py internal updates instead #TODO: use template.sequencer.py internal updates instead
cbox.Document.get_song().update_playback() cbox.Document.get_song().update_playback()
def startEngine(nsmClient): def startEngine(nsmClient):
@ -193,6 +193,7 @@ def startEngine(nsmClient):
#Send initial Callbacks to create the first GUI state. #Send initial Callbacks to create the first GUI state.
#The order of initial callbacks must not change to avoid GUI problems. #The order of initial callbacks must not change to avoid GUI problems.
#For example it is important that the tracks get created first and only then the number of measures #For example it is important that the tracks get created first and only then the number of measures
logger.info("Sending initial callbacks to GUI")
callbacks._numberOfTracksChanged() callbacks._numberOfTracksChanged()
callbacks._timeSignatureChanged() callbacks._timeSignatureChanged()
callbacks._numberOfMeasuresChanged() callbacks._numberOfMeasuresChanged()
@ -205,13 +206,14 @@ def startEngine(nsmClient):
session.data.buildAllTracks(buildSongDuration=True) #will set to max track length, we always have a song duration. session.data.buildAllTracks(buildSongDuration=True) #will set to max track length, we always have a song duration.
updatePlayback() updatePlayback()
logger.info("Patroneo api startEngine complete")
def _loopOff(): def _loopOff():
session.data.buildSongDuration() #no parameter removes the loop session.data.buildSongDuration() #no parameter removes the loop
updatePlayback() updatePlayback()
session.inLoopMode = None session.inLoopMode = None
callbacks._loopChanged(None, None, None) callbacks._loopChanged(None, None, None)
def _loopNow(): def _loopNow():
now = cbox.Transport.status().pos_ppqn now = cbox.Transport.status().pos_ppqn
@ -221,7 +223,7 @@ def _setLoop(loopMeasureAroundPpqn):
if loopMeasureAroundPpqn < 0: if loopMeasureAroundPpqn < 0:
_loopOff() _loopOff()
return return
loopStart, loopEnd = session.data.buildSongDuration(loopMeasureAroundPpqn) loopStart, loopEnd = session.data.buildSongDuration(loopMeasureAroundPpqn)
updatePlayback() updatePlayback()
@ -267,19 +269,19 @@ def set_quarterNotesPerMinute(value):
elif value == "on": elif value == "on":
assert not session.data.tempoMap.isTransportMaster assert not session.data.tempoMap.isTransportMaster
#keep old bpm value. 120 bpm is default. #keep old bpm value. 120 bpm is default.
session.data.tempoMap.isTransportMaster = True #triggers rebuild session.data.tempoMap.isTransportMaster = True #triggers rebuild
else: else:
assert value > 0 assert value > 0
session.data.tempoMap.setQuarterNotesPerMinute(value) session.data.tempoMap.setQuarterNotesPerMinute(value)
session.data.tempoMap.isTransportMaster = True #triggers rebuild session.data.tempoMap.isTransportMaster = True #triggers rebuild
#Does not need track rebuilding #Does not need track rebuilding
updatePlayback() updatePlayback()
callbacks._quarterNotesPerMinuteChanged() callbacks._quarterNotesPerMinuteChanged()
def set_whatTypeOfUnit(ticks): def set_whatTypeOfUnit(ticks):
"""Denominator of Time Signature""" """Denominator of Time Signature"""
if session.data.whatTypeOfUnit == ticks: return if session.data.whatTypeOfUnit == ticks: return
session.data.whatTypeOfUnit = ticks session.data.whatTypeOfUnit = ticks
session.data.buildAllTracks() session.data.buildAllTracks()
if session.inLoopMode: if session.inLoopMode:
@ -289,14 +291,14 @@ def set_whatTypeOfUnit(ticks):
def set_howManyUnits(value): def set_howManyUnits(value):
"""Numerator of Time Signature""" """Numerator of Time Signature"""
if session.data.howManyUnits == value: return if session.data.howManyUnits == value: return
session.data.howManyUnits = value session.data.howManyUnits = value
session.data.buildAllTracks() session.data.buildAllTracks()
if session.inLoopMode: if session.inLoopMode:
_loopNow() _loopNow()
updatePlayback() updatePlayback()
callbacks._timeSignatureChanged() callbacks._timeSignatureChanged()
def set_subdivisions(value): def set_subdivisions(value):
if session.data.subdivisions == value: return if session.data.subdivisions == value: return
@ -456,18 +458,18 @@ def trackMergeCopyFrom(sourceTrackId, targetTrackId):
targetTrack.buildTrack() targetTrack.buildTrack()
updatePlayback() updatePlayback()
callbacks._trackStructureChanged(targetTrack) callbacks._trackStructureChanged(targetTrack)
def trackPatternReplaceFrom(sourceTrackId, targetTrackId): def trackPatternReplaceFrom(sourceTrackId, targetTrackId):
if not sourceTrackId == targetTrackId: if not sourceTrackId == targetTrackId:
sourceTrack = session.data.trackById(sourceTrackId) sourceTrack = session.data.trackById(sourceTrackId)
targetTrack = session.data.trackById(targetTrackId) targetTrack = session.data.trackById(targetTrackId)
copyPattern = sourceTrack.pattern.copy(newParentTrack = targetTrack) copyPattern = sourceTrack.pattern.copy(newParentTrack = targetTrack)
targetTrack.pattern = copyPattern targetTrack.pattern = copyPattern
targetTrack.buildTrack() targetTrack.buildTrack()
updatePlayback() updatePlayback()
callbacks._patternChanged(targetTrack) callbacks._patternChanged(targetTrack)
def setSwitchScaleTranspose(trackId, position, transpose): def setSwitchScaleTranspose(trackId, position, transpose):
"""Scale transposition is flipped. lower value means higher pitch""" """Scale transposition is flipped. lower value means higher pitch"""
@ -498,32 +500,32 @@ def insertSilence(howMany, beforeMeasureNumber):
updatePlayback() updatePlayback()
def duplicateSwitchGroup(startMeasureForGroup:int, endMeasureExclusive:int): def duplicateSwitchGroup(startMeasureForGroup:int, endMeasureExclusive:int):
groupSize = endMeasureExclusive-startMeasureForGroup groupSize = endMeasureExclusive-startMeasureForGroup
insertSilence(groupSize, endMeasureExclusive) insertSilence(groupSize, endMeasureExclusive)
for track in session.data.tracks: for track in session.data.tracks:
for switch in range(startMeasureForGroup+groupSize, endMeasureExclusive+groupSize): #One group after the given one. for switch in range(startMeasureForGroup+groupSize, endMeasureExclusive+groupSize): #One group after the given one.
if switch-groupSize in track.structure: if switch-groupSize in track.structure:
track.structure.add(switch) track.structure.add(switch)
if switch-groupSize in track.whichPatternsAreScaleTransposed: if switch-groupSize in track.whichPatternsAreScaleTransposed:
track.whichPatternsAreScaleTransposed[switch] = track.whichPatternsAreScaleTransposed[switch-groupSize] track.whichPatternsAreScaleTransposed[switch] = track.whichPatternsAreScaleTransposed[switch-groupSize]
if switch-groupSize in track.whichPatternsAreHalftoneTransposed: if switch-groupSize in track.whichPatternsAreHalftoneTransposed:
track.whichPatternsAreHalftoneTransposed[switch] = track.whichPatternsAreHalftoneTransposed[switch-groupSize] track.whichPatternsAreHalftoneTransposed[switch] = track.whichPatternsAreHalftoneTransposed[switch-groupSize]
callbacks._trackStructureChanged(track) callbacks._trackStructureChanged(track)
session.data.buildAllTracks() session.data.buildAllTracks()
updatePlayback() updatePlayback()
def clearSwitchGroupTranspositions(startMeasureForGroup:int, endMeasureExclusive:int): def clearSwitchGroupTranspositions(startMeasureForGroup:int, endMeasureExclusive:int):
for track in session.data.tracks: for track in session.data.tracks:
for switch in range(startMeasureForGroup, endMeasureExclusive): for switch in range(startMeasureForGroup, endMeasureExclusive):
if switch in track.whichPatternsAreScaleTransposed: if switch in track.whichPatternsAreScaleTransposed:
del track.whichPatternsAreScaleTransposed[switch] del track.whichPatternsAreScaleTransposed[switch]
if switch in track.whichPatternsAreHalftoneTransposed: if switch in track.whichPatternsAreHalftoneTransposed:
del track.whichPatternsAreHalftoneTransposed[switch] del track.whichPatternsAreHalftoneTransposed[switch]
callbacks._trackStructureChanged(track) callbacks._trackStructureChanged(track)
session.data.buildAllTracks() session.data.buildAllTracks()
updatePlayback() updatePlayback()
def deleteSwitches(howMany, fromMeasureNumber): def deleteSwitches(howMany, fromMeasureNumber):
for track in session.data.tracks: for track in session.data.tracks:
new_structure = set() new_structure = set()
@ -650,35 +652,35 @@ def patternOffAllSteps(trackId):
track.buildTrack() track.buildTrack()
updatePlayback() updatePlayback()
callbacks._patternChanged(track) callbacks._patternChanged(track)
def patternInvertRow(trackId, pitchindex): def patternInvertRow(trackId, pitchindex):
"""Pitchindex is the row""" """Pitchindex is the row"""
track = session.data.trackById(trackId) track = session.data.trackById(trackId)
track.pattern.invertRow(pitchindex) track.pattern.invertRow(pitchindex)
track.pattern.buildExportCache() track.pattern.buildExportCache()
track.buildTrack() track.buildTrack()
updatePlayback() updatePlayback()
callbacks._patternChanged(track) callbacks._patternChanged(track)
def patternClearRow(trackId, pitchindex): def patternClearRow(trackId, pitchindex):
"""Pitchindex is the row. """Pitchindex is the row.
Index is the column""" Index is the column"""
track = session.data.trackById(trackId) track = session.data.trackById(trackId)
track.pattern.clearRow(pitchindex) track.pattern.clearRow(pitchindex)
track.pattern.buildExportCache() track.pattern.buildExportCache()
track.buildTrack() track.buildTrack()
updatePlayback() updatePlayback()
callbacks._patternChanged(track) callbacks._patternChanged(track)
def patternRowRepeatFromStep(trackId, pitchindex, index): def patternRowRepeatFromStep(trackId, pitchindex, index):
"""Pitchindex is the row. """Pitchindex is the row.
Index is the column""" Index is the column"""
track = session.data.trackById(trackId) track = session.data.trackById(trackId)
track.pattern.repeatFromStep(pitchindex, index) track.pattern.repeatFromStep(pitchindex, index)
track.pattern.buildExportCache() track.pattern.buildExportCache()
track.buildTrack() track.buildTrack()
updatePlayback() updatePlayback()
callbacks._patternChanged(track) callbacks._patternChanged(track)
def patternRowChangeVelocity(trackId, pitchindex, delta): def patternRowChangeVelocity(trackId, pitchindex, delta):
track = session.data.trackById(trackId) track = session.data.trackById(trackId)

83
engine/pattern.py

@ -36,8 +36,8 @@ class Pattern(object):
"""A pattern can be in only one track. """A pattern can be in only one track.
In fact having it as its own object is only for code readability In fact having it as its own object is only for code readability
A pattern is an unordered list of dicts. A pattern is an unordered list of dicts.
Each dict is an step, or a note. Each dict is an step, or a note.
{"index": from 0 to parentTrack.parentData.howManyUnits, {"index": from 0 to parentTrack.parentData.howManyUnits,
"factor": float, "factor": float,
"pitch": int 0-7, "pitch": int 0-7,
@ -61,6 +61,7 @@ class Pattern(object):
self.scale = scale if scale else (72, 71, 69, 67, 65, 64, 62, 60) #Scale needs to be set first because on init/load data already depends on it, at least the default scale. The scale is part of the track meta callback. self.scale = scale if scale else (72, 71, 69, 67, 65, 64, 62, 60) #Scale needs to be set first because on init/load data already depends on it, at least the default scale. The scale is part of the track meta callback.
self.data = data if data else list() #For content see docstring. this cannot be the default parameter because we would set the same list for all instances. self.data = data if data else list() #For content see docstring. this cannot be the default parameter because we would set the same list for all instances.
self.simpleNoteNames = simpleNoteNames if simpleNoteNames else self.parentTrack.parentData.lastUsedNotenames[:] #This is mostly for the GUI or other kinds of representation instead midi notes self.simpleNoteNames = simpleNoteNames if simpleNoteNames else self.parentTrack.parentData.lastUsedNotenames[:] #This is mostly for the GUI or other kinds of representation instead midi notes
assert self.simpleNoteNames
self._processAfterInit() self._processAfterInit()
def _prepareBeforeInit(self): def _prepareBeforeInit(self):
@ -77,11 +78,11 @@ class Pattern(object):
self._builtPatternCache = {} #holds a ready cbox pattern for a clip as value. Key is a tuple of hashable parameters. see self.buildPattern self._builtPatternCache = {} #holds a ready cbox pattern for a clip as value. Key is a tuple of hashable parameters. see self.buildPattern
def copy(self, newParentTrack): def copy(self, newParentTrack):
"""Return an independent copy of this pattern""" """Return an independent copy of this pattern"""
data = [note.copy() for note in self.data] #list of mutable dicts. Dicts have only primitve data types inside data = [note.copy() for note in self.data] #list of mutable dicts. Dicts have only primitve data types inside
scale = self.scale #it is immutable so there is no risk of changing it in place for both patterns at once scale = self.scale #it is immutable so there is no risk of changing it in place for both patterns at once
simpleNoteNames = self.simpleNoteNames[:] #this mutable list always gets replaced completely by setting a new list, but we don't want to take any chances and create a slice copy. simpleNoteNames = self.simpleNoteNames[:] #this mutable list always gets replaced completely by setting a new list, but we don't want to take any chances and create a slice copy.
result = Pattern(newParentTrack, data, scale, simpleNoteNames) result = Pattern(newParentTrack, data, scale, simpleNoteNames)
return result return result
@property @property
@ -137,80 +138,80 @@ class Pattern(object):
def _putRow(self, pitchindex, rowAsListOfSteps): def _putRow(self, pitchindex, rowAsListOfSteps):
"""Replace a row with the given one""" """Replace a row with the given one"""
self.clearRow(pitchindex) self.clearRow(pitchindex)
self.data.extend(rowAsListOfSteps) self.data.extend(rowAsListOfSteps)
def clearRow(self, pitchindex): def clearRow(self, pitchindex):
"""pure convenience. This could be done with """pure convenience. This could be done with
repeatFromStep on the first empty step""" repeatFromStep on the first empty step"""
existingSteps = self.getRow(pitchindex) existingSteps = self.getRow(pitchindex)
for step in existingSteps: for step in existingSteps:
self.data.remove(step) self.data.remove(step)
def _rowAsBooleans(self, pitchindex): def _rowAsBooleans(self, pitchindex):
"""Existence or not""" """Existence or not"""
existingSteps = self.getRow(pitchindex) existingSteps = self.getRow(pitchindex)
existingIndices = set(s["index"] for s in existingSteps) existingIndices = set(s["index"] for s in existingSteps)
result = [False] * self.parentTrack.parentData.howManyUnits result = [False] * self.parentTrack.parentData.howManyUnits
for i in existingIndices: for i in existingIndices:
result[i] = True result[i] = True
return result return result
def _getRowWithNoneFillers(self, pitchindex): def _getRowWithNoneFillers(self, pitchindex):
existingSteps = self.getRow(pitchindex) existingSteps = self.getRow(pitchindex)
result = [None] * self.parentTrack.parentData.howManyUnits result = [None] * self.parentTrack.parentData.howManyUnits
for st in existingSteps: for st in existingSteps:
result[st["index"]] = st result[st["index"]] = st
return result return result
def _old_repeatFromStep(self, pitchindex, stepIndex): def _old_repeatFromStep(self, pitchindex, stepIndex):
"""Includes the given step. """Includes the given step.
Uses average velocities Uses average velocities
""" """
vel = self.averageVelocity vel = self.averageVelocity
rowAsBools = self._rowAsBooleans(pitchindex) rowAsBools = self._rowAsBooleans(pitchindex)
toRepeatChunk = rowAsBools[:stepIndex+1] toRepeatChunk = rowAsBools[:stepIndex+1]
numberOfRepeats, rest = divmod(self.parentTrack.parentData.howManyUnits, stepIndex+1) numberOfRepeats, rest = divmod(self.parentTrack.parentData.howManyUnits, stepIndex+1)
index = 0 index = 0
newRow = [] newRow = []
for i in range(numberOfRepeats): for i in range(numberOfRepeats):
for b in toRepeatChunk: for b in toRepeatChunk:
if b: if b:
newRow.append({"index":index, "factor": 1, "pitch": pitchindex, "velocity":vel}) newRow.append({"index":index, "factor": 1, "pitch": pitchindex, "velocity":vel})
index += 1 index += 1
self._putRow(pitchindex, newRow) self._putRow(pitchindex, newRow)
def repeatFromStep(self, pitchindex, stepIndex): def repeatFromStep(self, pitchindex, stepIndex):
"""Includes the given step. """Includes the given step.
Uses original velocities and scale factors Uses original velocities and scale factors
""" """
originalRow = self._getRowWithNoneFillers(pitchindex) originalRow = self._getRowWithNoneFillers(pitchindex)
toRepeatChunk = originalRow[:stepIndex+1] toRepeatChunk = originalRow[:stepIndex+1]
numberOfRepeats, rest = divmod(self.parentTrack.parentData.howManyUnits, stepIndex+1) numberOfRepeats, rest = divmod(self.parentTrack.parentData.howManyUnits, stepIndex+1)
newRow = [] newRow = []
for i in range(numberOfRepeats): for i in range(numberOfRepeats):
for st in toRepeatChunk: for st in toRepeatChunk:
if st: if st:
s = st.copy() s = st.copy()
s["index"] = len(toRepeatChunk)*i + s["index"] s["index"] = len(toRepeatChunk)*i + s["index"]
newRow.append(s) newRow.append(s)
self._putRow(pitchindex, newRow) self._putRow(pitchindex, newRow)
def invertRow(self, pitchindex): def invertRow(self, pitchindex):
vel = self.averageVelocity vel = self.averageVelocity
existingSteps = self.getRow(pitchindex) existingSteps = self.getRow(pitchindex)
existingIndices = set(s["index"] for s in existingSteps) existingIndices = set(s["index"] for s in existingSteps)
for step in existingSteps: for step in existingSteps:
self.data.remove(step) self.data.remove(step)
for index in range(self.parentTrack.parentData.howManyUnits): for index in range(self.parentTrack.parentData.howManyUnits):
if not index in existingIndices: if not index in existingIndices:
self.data.append({"index":index, "factor": 1, "pitch": pitchindex, "velocity":vel}) self.data.append({"index":index, "factor": 1, "pitch": pitchindex, "velocity":vel})
def stepByIndexAndPitch(self, index, pitch): def stepByIndexAndPitch(self, index, pitch):
for d in self.data: for d in self.data:

10
qtgui/mainwindow.py

@ -157,9 +157,6 @@ class MainWindow(TemplateMainWindow):
#Toolbar, which needs the widgets above already established #Toolbar, which needs the widgets above already established
self._populateToolbar() self._populateToolbar()
#MainWindow Callbacks
api.callbacks.numberOfTracksChanged.append(self.callback_numberOfTracksChanged)
self.currentTrackId = None #this is purely a GUI construct. the engine does not know a current track. On startup there is no active track self.currentTrackId = None #this is purely a GUI construct. the engine does not know a current track. On startup there is no active track
self.start() #This shows the GUI, or not, depends on the NSM gui save setting. We need to call that after the menu, otherwise the about dialog will block and then we get new menu entries, which looks strange. self.start() #This shows the GUI, or not, depends on the NSM gui save setting. We need to call that after the menu, otherwise the about dialog will block and then we get new menu entries, which looks strange.
#There is always a track. Forcing that to be active is better than having to hide all the pattern widgets, or to disable them. #There is always a track. Forcing that to be active is better than having to hide all the pattern widgets, or to disable them.
@ -174,13 +171,6 @@ class MainWindow(TemplateMainWindow):
self.nsmClient.announceSaveStatus(isClean = True) self.nsmClient.announceSaveStatus(isClean = True)
def callback_numberOfTracksChanged(self, exportDictList):
"""We need to find out of the current track was the deleted one or if a new track got added
automatically."""
#if self.programStarted and len(exportDictList) == 1:
if len(exportDictList) == 1:
self.chooseCurrentTrack(exportDictList[0])
def chooseCurrentTrack(self, exportDict): def chooseCurrentTrack(self, exportDict):
"""This is in mainWindow because we need access to different sections of the program. """This is in mainWindow because we need access to different sections of the program.
newCurrentTrack is a backend track ID newCurrentTrack is a backend track ID

11
qtgui/pattern_grid.py

@ -614,7 +614,7 @@ class Scale(QtWidgets.QGraphicsRectItem):
super().__init__(0,0,0,0) super().__init__(0,0,0,0)
self.parentScene = parentScene self.parentScene = parentScene
self.pitchWidgets = [] #sorted from top to bottom in Step Rect and scene coordinates self.pitchWidgets = [] #sorted from top to bottom in Step Rect and scene coordinates
self.simpleNoteNames = [] #list of 128 notes. use index with note name. Can be changed at runtime. self.simpleNoteNames = None #list of 128 notes. use index with note name. Can be changed at runtime. Never empty.
api.callbacks.trackMetaDataChanged.append(self.callback_trackMetaDataChanged) api.callbacks.trackMetaDataChanged.append(self.callback_trackMetaDataChanged)
self.buildScale() #also sets the positions of the buttons above self.buildScale() #also sets the positions of the buttons above
@ -802,12 +802,13 @@ class PitchWidget(QtWidgets.QGraphicsProxyWidget):
def midiToNotename(self, midipitch): def midiToNotename(self, midipitch):
assert self.parentItem.simpleNoteNames, self.parentItem.simpleNoteNames assert self.parentItem.simpleNoteNames, (self.parentItem, self.parentItem.simpleNoteNames)
try: try:
return self.parentItem.simpleNoteNames[midipitch] #includes octave names return self.parentItem.simpleNoteNames[midipitch] #includes octave names
except IndexError: except IndexError as e:
print (midipitch) print (e)
print (self.parentItem.simpleNoteNames) print ("Midipitch:", midipitch)
print ("Simple Notename:", self.parentItem.simpleNoteNames)
exit() exit()
def spinBoxValueChanged(self): def spinBoxValueChanged(self):

Loading…
Cancel
Save