summaryrefslogtreecommitdiff
path: root/muse2
diff options
context:
space:
mode:
Diffstat (limited to 'muse2')
-rw-r--r--muse2/muse/arranger/pcanvas.cpp24
-rw-r--r--muse2/muse/functions.cpp29
-rw-r--r--muse2/muse/midiedit/scoreedit.cpp15
-rw-r--r--muse2/muse/part.cpp4
-rw-r--r--muse2/muse/part.h4
-rw-r--r--muse2/muse/song.cpp4
-rw-r--r--muse2/muse/song.h3
-rw-r--r--muse2/muse/undo.cpp60
-rw-r--r--muse2/muse/undo.h8
9 files changed, 106 insertions, 45 deletions
diff --git a/muse2/muse/arranger/pcanvas.cpp b/muse2/muse/arranger/pcanvas.cpp
index 91c0df5e..fde31c08 100644
--- a/muse2/muse/arranger/pcanvas.cpp
+++ b/muse2/muse/arranger/pcanvas.cpp
@@ -484,14 +484,23 @@ void PartCanvas::partsChanged()
//---------------------------------------------------------
void PartCanvas::updateSelection()
- {
+{
+ Undo operations;
+ bool changed=false;
for (iCItem i = items.begin(); i != items.end(); ++i) {
NPart* part = (NPart*)(i->second);
- part->part()->setSelected(i->second->isSelected());
+ operations.push_back(UndoOp(UndoOp::SelectPart, part->part(), i->second->isSelected(), part->part()->selected()));
+ if (i->second->isSelected() != part->part()->selected())
+ changed=true;
}
- emit selectionChanged();
- redraw();
+
+ if (changed)
+ {
+ MusEGlobal::song->applyOperationGroup(operations);
+ emit selectionChanged();
+ redraw();
}
+}
//---------------------------------------------------------
// resizeItem
@@ -886,13 +895,14 @@ void PartCanvas::itemPopup(CItem* item, int n, const QPoint& pt)
// The loop is a safety net.
MusECore::Part* p = part;
+ Undo operations;
if(part->hasClones())
{
- p->setSelected(true);
+ operations.push_back(UndoOp(UndoOp::SelectPart, p, true, p->selected()));
for(MusECore::Part* it = p->nextClone(); it!=p; it=it->nextClone())
- it->setSelected(true);
+ operations.push_back(UndoOp(UndoOp::SelectPart, it, true, it->selected()));
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperationGroup(operations);
}
break;
diff --git a/muse2/muse/functions.cpp b/muse2/muse/functions.cpp
index c2941a72..7d5547cb 100644
--- a/muse2/muse/functions.cpp
+++ b/muse2/muse/functions.cpp
@@ -1228,59 +1228,64 @@ void paste_at(const QString& pt, int pos, int max_distance, bool always_new_part
void select_all(const set<const Part*>& parts)
{
+ Undo operations;
for (set<const Part*>::iterator part=parts.begin(); part!=parts.end(); part++)
for (ciEvent ev_it=(*part)->events().begin(); ev_it!=(*part)->events().end(); ev_it++)
{
const Event& event=ev_it->second;
- event.setSelected(true);
+ operations.push_back(UndoOp(UndoOp::SelectEvent,event, true, event.selected()));
}
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperationGroup(operations);
}
void select_none(const set<const Part*>& parts)
{
+ Undo operations;
for (set<const Part*>::iterator part=parts.begin(); part!=parts.end(); part++)
for (ciEvent ev_it=(*part)->events().begin(); ev_it!=(*part)->events().end(); ev_it++)
{
const Event& event=ev_it->second;
- event.setSelected(false);
+ operations.push_back(UndoOp(UndoOp::SelectEvent,event, false, event.selected()));
}
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperationGroup(operations);
}
void select_invert(const set<const Part*>& parts)
{
+ Undo operations;
for (set<const Part*>::iterator part=parts.begin(); part!=parts.end(); part++)
for (ciEvent ev_it=(*part)->events().begin(); ev_it!=(*part)->events().end(); ev_it++)
{
const Event& event=ev_it->second;
- event.setSelected(!event.selected());
+ operations.push_back(UndoOp(UndoOp::SelectEvent,event, !event.selected(), event.selected()));
}
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperationGroup(operations);
}
void select_in_loop(const set<const Part*>& parts)
{
- select_none(parts);
+ select_none(parts); // this will automatically be grouped into one OperationGroup
+ Undo operations;
for (set<const Part*>::iterator part=parts.begin(); part!=parts.end(); part++)
for (ciEvent ev_it=(*part)->events().begin(); ev_it!=(*part)->events().end(); ev_it++)
{
const Event& event=ev_it->second;
- event.setSelected((event.tick()>=MusEGlobal::song->lpos() && event.endTick()<=MusEGlobal::song->rpos()));
+ operations.push_back(UndoOp(UndoOp::SelectEvent,event, (event.tick()>=MusEGlobal::song->lpos() && event.endTick()<=MusEGlobal::song->rpos()), event.selected()));
}
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperationGroup(operations);
}
void select_not_in_loop(const set<const Part*>& parts)
{
- select_none(parts);
+ select_none(parts); // this will automatically be grouped into one OperationGroup
+ Undo operations;
for (set<const Part*>::iterator part=parts.begin(); part!=parts.end(); part++)
for (ciEvent ev_it=(*part)->events().begin(); ev_it!=(*part)->events().end(); ev_it++)
{
const Event& event=ev_it->second;
- event.setSelected(!(event.tick()>=MusEGlobal::song->lpos() && event.endTick()<=MusEGlobal::song->rpos()));
+ operations.push_back(UndoOp(UndoOp::SelectEvent,event, !(event.tick()>=MusEGlobal::song->lpos() && event.endTick()<=MusEGlobal::song->rpos()), event.selected()));
}
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperationGroup(operations);
}
diff --git a/muse2/muse/midiedit/scoreedit.cpp b/muse2/muse/midiedit/scoreedit.cpp
index 1b8daefc..96fcc5a5 100644
--- a/muse2/muse/midiedit/scoreedit.cpp
+++ b/muse2/muse/midiedit/scoreedit.cpp
@@ -73,6 +73,7 @@ using namespace std;
using MusEGlobal::debugMsg;
using MusEGlobal::heavyDebugMsg;
+using MusECore::UndoOp;
namespace MusEGui {
@@ -3927,9 +3928,7 @@ void ScoreCanvas::mouseReleaseEvent (QMouseEvent* event)
if (!ctrl)
deselect_all();
- clicked_event_ptr->setSelected(!clicked_event_ptr->selected());
-
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperation(UndoOp(UndoOp::SelectEvent, *clicked_event_ptr, !clicked_event_ptr->selected(), clicked_event_ptr->selected()));
}
setMouseTracking(false);
@@ -4028,9 +4027,7 @@ void ScoreCanvas::mouseMoveEvent (QMouseEvent* event)
if (!ctrl)
deselect_all();
- clicked_event_ptr->setSelected(true);
-
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperation(UndoOp(UndoOp::SelectEvent, *clicked_event_ptr, true, clicked_event_ptr->selected()));
}
old_pitch=-1;
@@ -4508,9 +4505,7 @@ void ScoreCanvas::deselect_all()
for (set<const MusECore::Part*>::iterator part=all_parts.begin(); part!=all_parts.end(); part++)
for (MusECore::ciEvent event=(*part)->events().begin(); event!=(*part)->events().end(); event++)
- event->second.setSelected(false);
-
- MusEGlobal::song->update(SC_SELECTION);
+ MusEGlobal::song->applyOperation(UndoOp(UndoOp::SelectEvent, event->second, false, event->second.selected()));
}
bool staff_t::cleanup_parts()
@@ -4568,7 +4563,7 @@ void staff_t::apply_lasso(QRect rect, set<const MusECore::Event*>& already_proce
if (rect.contains(it2->x, it2->y))
if (already_processed.find(it2->source_event)==already_processed.end())
{
- it2->source_event->setSelected(!it2->source_event->selected());
+ MusEGlobal::song->applyOperation(UndoOp(UndoOp::SelectEvent,*it2->source_event,!it2->source_event->selected(),it2->source_event->selected()));
already_processed.insert(it2->source_event);
}
}
diff --git a/muse2/muse/part.cpp b/muse2/muse/part.cpp
index 9c3f0e38..e25643c8 100644
--- a/muse2/muse/part.cpp
+++ b/muse2/muse/part.cpp
@@ -96,7 +96,7 @@ void Part::rechainClone()
// unchainTrackParts
//---------------------------------------------------------
-void unchainTrackParts(Track* t, bool decRefCount)
+void unchainTrackParts(Track* t)
{
PartList* pl = t->parts();
for(iPart ip = pl->begin(); ip != pl->end(); ++ip)
@@ -107,7 +107,7 @@ void unchainTrackParts(Track* t, bool decRefCount)
// chainTrackParts
//---------------------------------------------------------
-void chainTrackParts(Track* t, bool incRefCount)
+void chainTrackParts(Track* t)
{
PartList* pl = t->parts();
for(riPart ip = pl->rbegin(); ip != pl->rend(); ++ip) // walk through in opposite direction than we unchained them.
diff --git a/muse2/muse/part.h b/muse2/muse/part.h
index d128460b..ea19410d 100644
--- a/muse2/muse/part.h
+++ b/muse2/muse/part.h
@@ -196,8 +196,8 @@ class PartList : public std::multimap<int, Part*, std::less<unsigned> > {
};
extern void chainCheckErr(Part* p);
-extern void unchainTrackParts(Track* t, bool decRefCount);
-extern void chainTrackParts(Track* t, bool incRefCount);
+extern void unchainTrackParts(Track* t);
+extern void chainTrackParts(Track* t);
extern void addPortCtrlEvents(Part* part, bool doClones);
extern void addPortCtrlEvents(Event& event, Part* part, bool doClones);
extern void removePortCtrlEvents(Part* part, bool doClones);
diff --git a/muse2/muse/song.cpp b/muse2/muse/song.cpp
index 5c755a9d..4e70adf5 100644
--- a/muse2/muse/song.cpp
+++ b/muse2/muse/song.cpp
@@ -3224,12 +3224,12 @@ void Song::removeTrack2(Track* track)
case Track::DRUM:
case Track::NEW_DRUM:
removePortCtrlEvents(((MidiTrack*)track));
- unchainTrackParts(track, true);
+ unchainTrackParts(track);
_midis.erase(track);
break;
case Track::WAVE:
- unchainTrackParts(track, true);
+ unchainTrackParts(track);
_waves.erase(track);
break;
diff --git a/muse2/muse/song.h b/muse2/muse/song.h
index 91745c96..95a383cd 100644
--- a/muse2/muse/song.h
+++ b/muse2/muse/song.h
@@ -171,7 +171,8 @@ class Song : public QObject {
Song(const char* name = 0);
~Song();
- bool applyOperationGroup(Undo& group, bool doUndo=true);
+ bool applyOperationGroup(Undo& group, bool doUndo=true); // group may be changed! cleanOperationGroup is called on group!
+ bool applyOperation(const UndoOp& op, bool doUndo=true);
/** this sends emits a signal to each MidiEditor or whoever is interested.
* For each part which is 1) opened in this MidiEditor and 2) which is
diff --git a/muse2/muse/undo.cpp b/muse2/muse/undo.cpp
index f49d3990..5dbe1e9e 100644
--- a/muse2/muse/undo.cpp
+++ b/muse2/muse/undo.cpp
@@ -52,8 +52,8 @@ const char* UndoOp::typeName()
{
static const char* name[] = {
"AddTrack", "DeleteTrack",
- "AddPart", "DeletePart", "ModifyPartTick", "ModifyPartLength", "ModifyPartLengthFrames", "ModifyPartName",
- "AddEvent", "DeleteEvent", "ModifyEvent",
+ "AddPart", "DeletePart", "ModifyPartTick", "ModifyPartLength", "ModifyPartLengthFrames", "ModifyPartName", "SelectPart",
+ "AddEvent", "DeleteEvent", "ModifyEvent", "SelectEvent",
"AddTempo", "DeleteTempo",
"AddSig", "DeleteSig",
"AddKey", "DeleteKey",
@@ -305,6 +305,12 @@ void cleanOperationGroup(Undo& group)
}
}
+bool Song::applyOperation(const UndoOp& op, bool doUndo)
+{
+ Undo operations;
+ operations.push_back(op);
+ return applyOperationGroup(operations, doUndo);
+}
bool Song::applyOperationGroup(Undo& group, bool doUndo)
{
@@ -353,9 +359,9 @@ void Song::doUndo2()
removeTrack2(editable_track);
updateFlags |= SC_TRACK_REMOVED;
break;
- case UndoOp::DeleteTrack: // FINDMICHJETZT FIXME TODO: DeletePart on all parts, only empty tracks may be deleted! this removes the necessarity of unchainTrackParts...
+ case UndoOp::DeleteTrack: // FINDMICHJETZT FIXME TODO: DeletePart on all parts, only empty tracks may be deleted! this removes the necessarity of un...
insertTrack2(editable_track, i->trackno);
- chainTrackParts(editable_track, true);
+ chainTrackParts(editable_track);
updateFlags |= SC_TRACK_INSERTED;
break;
@@ -472,7 +478,7 @@ void Song::doRedo2()
switch(i->type) {
case UndoOp::AddTrack:
insertTrack2(editable_track, i->trackno);
- chainTrackParts(editable_track, true);
+ chainTrackParts(editable_track);
updateFlags |= SC_TRACK_INSERTED;
break;
@@ -613,6 +619,18 @@ UndoOp::UndoOp(UndoType type_, const Part* part_, unsigned old_len_or_tick, unsi
old_partlen_or_tick=old_len_or_tick;
new_partlen_or_tick=new_len_or_tick;
}
+
+UndoOp::UndoOp(UndoType type_, const Part* part_, bool selected_, bool sel_old_)
+{
+ assert(type_==SelectPart);
+ assert(part);
+
+ type=type_;
+ part = part_;
+ selected=selected_;
+ selected_old=sel_old_;
+}
+
UndoOp::UndoOp(UndoType type_, const Event& oev, const Event& nev, const Part* part_, bool doCtrls_, bool doClones_)
{
@@ -638,6 +656,16 @@ UndoOp::UndoOp(UndoType type_, const Event& nev, const Part* part_, bool doCtrls
doCtrls = doCtrls_;
doClones = doClones_;
}
+
+UndoOp::UndoOp(UndoType type_, const Event& nev, bool selected_, bool sel_old_)
+{
+ assert(type_==SelectEvent);
+
+ type=type_;
+ nEvent = nev;
+ selected=selected_;
+ selected_old=sel_old_;
+}
UndoOp::UndoOp(UndoType type_, Marker* copyMarker_, Marker* realMarker_)
@@ -737,8 +765,17 @@ bool Song::doUndo1()
for (riUndoOp i = u.rbegin(); i != u.rend(); ++i) {
Track* editable_track = const_cast<Track*>(i->track);
Track* editable_property_track = const_cast<Track*>(i->_propertyTrack);
-// uncomment if needed Part* editable_part = const_cast<Part*>(i->part);
+ Part* editable_part = const_cast<Part*>(i->part);
switch(i->type) {
+ case UndoOp::SelectPart:
+ editable_part->setSelected(i->selected_old);
+ updateFlags |= SC_SELECTION;
+ break;
+ case UndoOp::SelectEvent:
+ i->nEvent.setSelected(i->selected_old);
+ updateFlags |= SC_SELECTION;
+ break;
+
case UndoOp::AddTrack:
removeTrack1(editable_track);
break;
@@ -871,8 +908,17 @@ bool Song::doRedo1()
for (iUndoOp i = u.begin(); i != u.end(); ++i) {
Track* editable_track = const_cast<Track*>(i->track);
Track* editable_property_track = const_cast<Track*>(i->_propertyTrack);
-// uncomment if needed Part* editable_part = const_cast<Part*>(i->part);
+ Part* editable_part = const_cast<Part*>(i->part);
switch(i->type) {
+ case UndoOp::SelectPart:
+ editable_part->setSelected(i->selected);
+ updateFlags |= SC_SELECTION;
+ break;
+ case UndoOp::SelectEvent:
+ i->nEvent.setSelected(i->selected);
+ updateFlags |= SC_SELECTION;
+ break;
+
case UndoOp::AddTrack:
insertTrack1(editable_track, i->trackno);
diff --git a/muse2/muse/undo.h b/muse2/muse/undo.h
index 9997d4cb..6c372624 100644
--- a/muse2/muse/undo.h
+++ b/muse2/muse/undo.h
@@ -46,8 +46,8 @@ extern std::list<QString> temporaryWavFiles; //!< Used for storing all tmp-files
struct UndoOp {
enum UndoType {
AddTrack, DeleteTrack,
- AddPart, DeletePart, ModifyPartTick, ModifyPartLength, ModifyPartLengthFrames, /* FINDMICH FIXME frames are to be deprecated */ ModifyPartName,
- AddEvent, DeleteEvent, ModifyEvent,
+ AddPart, DeletePart, ModifyPartTick, ModifyPartLength, ModifyPartLengthFrames, /* FINDMICH FIXME frames are to be deprecated */ ModifyPartName, SelectPart,
+ AddEvent, DeleteEvent, ModifyEvent, SelectEvent,
AddTempo, DeleteTempo,
AddSig, DeleteSig,
AddKey, DeleteKey,
@@ -102,6 +102,8 @@ struct UndoOp {
char* _newName;
Event oEvent;
Event nEvent;
+ bool selected;
+ bool selected_old;
bool doCtrls;
bool doClones;
@@ -113,8 +115,10 @@ struct UndoOp {
UndoOp(UndoType type, int n, const Track* track);
UndoOp(UndoType type, const Part* part, unsigned old_len_or_tick=-1, unsigned new_len_or_tick=-1, bool doCtrls=false, bool doClones=false); // FIXME these bools are UNUSED!!. XTICKS!
UndoOp(UndoType type, const Part* part, const char* old_name, const char* new_name);
+ UndoOp(UndoType type, const Part* part, bool selected, bool selected_old);
UndoOp(UndoType type, const Event& oev, const Event& nev, const Part* part, bool doCtrls, bool doClones);
UndoOp(UndoType type, const Event& nev, const Part* part, bool doCtrls, bool doClones);
+ UndoOp(UndoType type, const Event& nev, bool selected, bool selected_old);
UndoOp(UndoType type, const char* changedFile, const char* changeData, int startframe, int endframe);
UndoOp(UndoType type, Marker* copyMarker, Marker* realMarker);
UndoOp(UndoType type, const Track* track, const char* old_name, const char* new_name);