summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--muse2/muse/arranger/pcanvas.cpp182
-rw-r--r--muse2/muse/audio.cpp4
-rw-r--r--muse2/muse/audio.h6
-rw-r--r--muse2/muse/functions.cpp28
-rw-r--r--muse2/muse/midiseq.cpp3
-rw-r--r--muse2/muse/part.cpp62
-rw-r--r--muse2/muse/seqmsg.cpp15
-rw-r--r--muse2/muse/song.cpp69
-rw-r--r--muse2/muse/song.h2
-rw-r--r--muse2/muse/structure.cpp63
-rw-r--r--muse2/muse/undo.cpp125
-rw-r--r--muse2/muse/undo.h23
12 files changed, 229 insertions, 353 deletions
diff --git a/muse2/muse/arranger/pcanvas.cpp b/muse2/muse/arranger/pcanvas.cpp
index 646a9382..0e1e04a8 100644
--- a/muse2/muse/arranger/pcanvas.cpp
+++ b/muse2/muse/arranger/pcanvas.cpp
@@ -64,6 +64,10 @@
#include "utils.h"
#include "dialogs.h"
#include "widgets/pastedialog.h"
+#include "undo.h"
+
+using MusECore::Undo;
+using MusECore::UndoOp;
#define ABS(x) (abs(x))
@@ -189,12 +193,12 @@ void PartCanvas::returnPressed()
if (editMode) {
//this check is neccessary, because it returnPressed may be called
//twice. the second call would cause a crash, however!
- MusECore::Part* oldPart = editPart->part();
- MusECore::Part* newPart = oldPart->clone();
-
- newPart->setName(lineEditor->text());
+ MusECore::Part* part = editPart->part();
// Indicate do undo, and do port controller values but not clone parts.
- MusEGlobal::audio->msgChangePart(oldPart, newPart, true, true, false);
+
+ Undo operations;
+ operations.push_back(UndoOp(UndoOp::ModifyPartName,part, part->name().toUtf8().data(), lineEditor->text().toUtf8().data())); // FIXME char sucks, better use QString directly.
+ MusEGlobal::song->applyOperationGroup(operations);
editMode = false;
@@ -314,7 +318,7 @@ void PartCanvas::moveCanvasItems(CItemList& items, int dp, int dx, DragType dtyp
bool result=moveItem(operations, ci, newpos, dtype);
if (result)
- ci->move(newpos);
+ ci->move(newpos);
if(moving.size() == 1) {
itemReleased(curItem, newpos);
@@ -333,102 +337,89 @@ void PartCanvas::moveCanvasItems(CItemList& items, int dp, int dx, DragType dtyp
//---------------------------------------------------------
bool PartCanvas::moveItem(MusECore::Undo& operations, CItem* item, const QPoint& newpos, DragType t)
- {
- NPart* npart = (NPart*) item;
- MusECore::Part* spart = npart->part();
- MusECore::Track* track = npart->track();
- MusECore::Track* dtrack=NULL;
- unsigned dtick = newpos.x();
- unsigned ntrack = y2pitch(item->mp().y());
- MusECore::Track::TrackType type = track->type();
- if (tracks->index(track) == ntrack && (dtick == spart->tick())) {
- return false;
- }
- if (ntrack >= tracks->size()) {
- ntrack = tracks->size();
- if (MusEGlobal::debugMsg)
- printf("PartCanvas::moveItem - add new track\n");
- dtrack = MusEGlobal::song->addTrack(operations, type); // Add at end of list.
-
- if (type == MusECore::Track::WAVE) {
- MusECore::WaveTrack* st = (MusECore::WaveTrack*) track;
- MusECore::WaveTrack* dt = (MusECore::WaveTrack*) dtrack;
- dt->setChannels(st->channels());
- }
- emit tracklistChanged();
- }
- else
- {
- dtrack = tracks->index(ntrack);
- if (dtrack->type() != type) {
- QMessageBox::critical(this, QString("MusE"),
- tr("Cannot copy/move/clone to different Track-Type"));
- return false;
- }
- }
-
- MusECore::Part* dpart;
- bool clone = (t == MOVE_CLONE || (t == MOVE_COPY && spart->events()->arefCount() > 1));
-
- if(t == MOVE_MOVE)
- {
- // This doesn't increment aref count, and doesn't chain clones.
- // It also gives the new part a new serial number, but it is
- // overwritten with the old one by Song::changePart(), from Audio::msgChangePart() below.
- dpart = spart->clone();
- dpart->setTrack(dtrack);
- }
- else
+{
+ NPart* npart = (NPart*) item;
+ MusECore::Part* spart = npart->part();
+ MusECore::Track* track = npart->track();
+ MusECore::Track* dtrack=NULL;
+ unsigned dtick = newpos.x(); // FIXME TODO make subtick-compatible!
+ unsigned ntrack = y2pitch(item->mp().y());
+ MusECore::Track::TrackType type = track->type();
+ int new_partend;
+ if (tracks->index(track) == ntrack && (dtick == spart->tick())) {
+ return false;
+ }
+ if (ntrack >= tracks->size()) {
+ ntrack = tracks->size();
+ if (MusEGlobal::debugMsg)
+ printf("PartCanvas::moveItem - add new track\n");
+ dtrack = MusEGlobal::song->addTrack(operations, type); // Add at end of list.
+
+ if (type == MusECore::Track::WAVE) {
+ MusECore::WaveTrack* st = (MusECore::WaveTrack*) track;
+ MusECore::WaveTrack* dt = (MusECore::WaveTrack*) dtrack;
+ dt->setChannels(st->channels());
+ }
+ emit tracklistChanged();
+ }
+ else
+ {
+ dtrack = tracks->index(ntrack);
+ if (dtrack->type() != type) {
+ QMessageBox::critical(this, QString("MusE"),
+ tr("Cannot copy/move/clone to different Track-Type"));
+ return false;
+ }
+ }
+
+
+
+ if(t == MOVE_MOVE)
+ {
+ operations.push_back(MusECore::UndoOp(MusECore::UndoOp::ModifyPartTick,spart,spart->tick(),dtick));
+
+ new_partend=(spart->lenTick() + dtick);
+ }
+ else
+ {
+ MusECore::Part* dpart;
+ bool clone = (t == MOVE_CLONE || (t == MOVE_COPY && spart->events()->arefCount() > 1));
+
// This increments aref count if cloned, and chains clones.
// It also gives the new part a new serial number.
dpart = dtrack->newPart(spart, clone);
-
- dpart->setTick(dtick);
-
- if(t == MOVE_MOVE)
- item->setPart(dpart);
- if (t == MOVE_COPY && !clone) {
+
+ dpart->setTick(dtick);
+ if (t == MOVE_COPY && !clone) {
// Copy Events
MusECore::EventList* se = spart->events();
MusECore::EventList* de = dpart->events();
for (MusECore::iEvent i = se->begin(); i != se->end(); ++i) {
- MusECore::Event oldEvent = i->second;
- MusECore::Event ev = oldEvent.clone();
- de->add(ev);
- }
+ MusECore::Event oldEvent = i->second;
+ MusECore::Event ev = oldEvent.clone();
+ de->add(ev);
}
-
-
- if (t == MOVE_COPY || t == MOVE_CLONE) {
- dpart->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it
- // so we must decrement it first :/
- // These will not increment ref count, and will not chain clones...
- // TODO DELETETHIS: is the above comment still correct (by flo93)? i doubt it!
- operations.push_back(MusECore::UndoOp(MusECore::UndoOp::AddPart,dpart));
- }
- else if (t == MOVE_MOVE) {
- // In all cases found ev lists were same. So this is redundant - Redo incs then decs the same list.
- // But just in case we ever have two different lists...
- dpart->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it
- // so we must decrement it first :/
- spart->events()->incARef(1); // the later MusEGlobal::song->applyOperationGroup() will decrement it
- // so we must increment it first :/
- dpart->setSelected(spart->selected());
- // These will increment ref count if not a clone, and will chain clones...
- // TODO DELETETHIS: is the above comment still correct (by flo93)? i doubt it!
- operations.push_back(MusECore::UndoOp(MusECore::UndoOp::ModifyPart,spart, dpart, true, false));
-
- spart->setSelected(false);
- }
- // else // will never happen -> operations will never be empty
-
- if (MusEGlobal::song->len() < (dpart->lenTick() + dpart->tick()))
+ }
+
+ dpart->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it
+ // so we must decrement it first :/
+ // These will not increment ref count, and will not chain clones...
+ // TODO DELETETHIS: is the above comment still correct (by flo93)? i doubt it!
+ operations.push_back(MusECore::UndoOp(MusECore::UndoOp::AddPart,dpart));
+
+ new_partend=(dpart->lenTick() + dpart->tick());
+
+ }
+
+ if (MusEGlobal::song->len() < new_partend) // FIXME this is buggy anyway.
operations.push_back( MusECore::UndoOp(MusECore::UndoOp::ModifySongLen,
- dpart->lenTick() + dpart->tick(),
+ new_partend,
MusEGlobal::song->len() ) );
-
- return true;
- }
+
+
+
+ return true;
+}
//---------------------------------------------------------
// raster
@@ -866,9 +857,10 @@ void PartCanvas::itemPopup(CItem* item, int n, const QPoint& pt)
MusECore::Event ev = oldEvent.clone();
de->add(ev);
}
- // Indicate undo, and do port controller values but not clone parts.
- // changed by flo93: removed start and endUndo, instead changed first bool to true
- MusEGlobal::audio->msgChangePart(spart, dpart, true, true, false);
+ Undo operations;
+ operations.push_back(UndoOp(UndoOp::DeletePart, spart));
+ operations.push_back(UndoOp(UndoOp::AddPart, dpart));
+ MusEGlobal::song->applyOperationGroup(operations);
break;
}
case 16: // Export to file
diff --git a/muse2/muse/audio.cpp b/muse2/muse/audio.cpp
index 659ae8a9..bbc803c5 100644
--- a/muse2/muse/audio.cpp
+++ b/muse2/muse/audio.cpp
@@ -76,9 +76,9 @@ void initAudio()
extern double curTime();
const char* seqMsgList[] = {
- "SEQM_ADD_TRACK", "SEQM_REMOVE_TRACK", //"SEQM_CHANGE_TRACK", DELETETHIS
+ "SEQM_ADD_TRACK", "SEQM_REMOVE_TRACK",
"SEQM_MOVE_TRACK",
- "SEQM_ADD_PART", "SEQM_REMOVE_PART", "SEQM_CHANGE_PART",
+ "SEQM_ADD_PART", "SEQM_REMOVE_PART",
"SEQM_ADD_EVENT", "SEQM_REMOVE_EVENT", "SEQM_CHANGE_EVENT",
"SEQM_ADD_TEMPO", "SEQM_SET_TEMPO", "SEQM_REMOVE_TEMPO", "SEQM_ADD_SIG", "SEQM_REMOVE_SIG",
"SEQM_SET_GLOBAL_TEMPO",
diff --git a/muse2/muse/audio.h b/muse2/muse/audio.h
index a403e5bf..e8d22f78 100644
--- a/muse2/muse/audio.h
+++ b/muse2/muse/audio.h
@@ -60,9 +60,9 @@ class Track;
//---------------------------------------------------------
enum {
- SEQM_ADD_TRACK, SEQM_REMOVE_TRACK, //SEQM_CHANGE_TRACK, DELETETHIS
+ SEQM_ADD_TRACK, SEQM_REMOVE_TRACK,
SEQM_MOVE_TRACK,
- SEQM_ADD_PART, SEQM_REMOVE_PART, SEQM_CHANGE_PART,
+ SEQM_ADD_PART, SEQM_REMOVE_PART,
SEQM_ADD_EVENT, SEQM_REMOVE_EVENT, SEQM_CHANGE_EVENT,
SEQM_ADD_TEMPO, SEQM_SET_TEMPO, SEQM_REMOVE_TEMPO, SEQM_ADD_SIG, SEQM_REMOVE_SIG,
SEQM_ADD_KEY, SEQM_REMOVE_KEY,
@@ -234,11 +234,9 @@ class Audio {
void msgRemoveTrack(Track*, bool u = true);
void msgRemoveTracks();
- //void msgChangeTrack(Track* oldTrack, Track* newTrack, bool u = true); DELETETHIS
void msgMoveTrack(int idx1, int dx2, bool u = true);
void msgAddPart(Part*, bool u = true);
void msgRemovePart(Part*, bool u = true);
- void msgChangePart(Part* oldPart, Part* newPart, bool u = true, bool doCtrls = true, bool doClones = false);
void msgAddEvent(Event&, Part*, bool u = true, bool doCtrls = true, bool doClones = false);
void msgDeleteEvent(Event&, Part*, bool u = true, bool doCtrls = true, bool doClones = false);
void msgChangeEvent(Event&, Event&, Part*, bool u = true, bool doCtrls = true, bool doClones = false);
diff --git a/muse2/muse/functions.cpp b/muse2/muse/functions.cpp
index fa53f5d4..449461c5 100644
--- a/muse2/muse/functions.cpp
+++ b/muse2/muse/functions.cpp
@@ -2,7 +2,7 @@
// MusE
// Linux Music Editor
// $Id: functions.cpp,v 1.20.2.19 2011/05/05 20:10 flo93 Exp $
-// (C) Copyright 2011 Florian Jung (flo93@sourceforge.net)
+// (C) Copyright 2011,2013 Florian Jung (flo93@sourceforge.net)
//
// This program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public License
@@ -1310,11 +1310,7 @@ void shrink_parts(int raster)
if (len<min_len) len=min_len;
if (len < part->second->lenTick())
- {
- MidiPart* new_part = new MidiPart(*(MidiPart*)part->second);
- new_part->setLenTick(len);
- operations.push_back(UndoOp(UndoOp::ModifyPart, part->second, new_part, true, false));
- }
+ operations.push_back(UndoOp(UndoOp::ModifyPartLength, part->second, part->second->lenTick(), len, true, false));
}
MusEGlobal::song->applyOperationGroup(operations);
@@ -1326,8 +1322,8 @@ void schedule_resize_all_same_len_clone_parts(Part* part, unsigned new_len, Undo
QSet<const Part*> already_done;
for (Undo::iterator op_it=operations.begin(); op_it!=operations.end();op_it++)
- if (op_it->type==UndoOp::ModifyPart || op_it->type==UndoOp::DeletePart)
- already_done.insert(op_it->nPart);
+ if (op_it->type==UndoOp::DeletePart)
+ already_done.insert(op_it->part);
unsigned old_len= part->type() == Pos::FRAMES ? part->lenFrame() : part->lenTick();
if (old_len!=new_len)
@@ -1338,18 +1334,12 @@ void schedule_resize_all_same_len_clone_parts(Part* part, unsigned new_len, Undo
if (part->type() == Pos::FRAMES)
{
if (part_it->lenFrame()==old_len && !already_done.contains(part_it))
- {
- WavePart* new_part = new WavePart(*(WavePart*)part_it);
- new_part->setLenFrame(new_len);
- operations.push_back(UndoOp(UndoOp::ModifyPart, part_it, new_part, true, false));
- }
+ operations.push_back(UndoOp(UndoOp::ModifyPartLengthFrames, part_it, part_it->lenFrame(), new_len, true, false)); // FIXME FINDMICH frames suck :(
}
else
if (part_it->lenTick()==old_len && !already_done.contains(part_it))
{
- MidiPart* new_part = new MidiPart(*(MidiPart*)part_it);
- new_part->setLenTick(new_len);
- operations.push_back(UndoOp(UndoOp::ModifyPart, part_it, new_part, true, false));
+ operations.push_back(UndoOp(UndoOp::ModifyPartLength, part_it, part_it->lenTick(), new_len, true, false));
}
part_it=part_it->nextClone();
@@ -1381,11 +1371,7 @@ void expand_parts(int raster)
if (len<min_len) len=min_len;
if (len > part->second->lenTick())
- {
- MidiPart* new_part = new MidiPart(*(MidiPart*)part->second);
- new_part->setLenTick(len);
- operations.push_back(UndoOp(UndoOp::ModifyPart, part->second, new_part, true, false));
- }
+ operations.push_back(UndoOp(UndoOp::ModifyPartLength, part->second, part->second->lenTick(), len, true, false));
}
MusEGlobal::song->applyOperationGroup(operations);
diff --git a/muse2/muse/midiseq.cpp b/muse2/muse/midiseq.cpp
index b94e284e..8aa6c289 100644
--- a/muse2/muse/midiseq.cpp
+++ b/muse2/muse/midiseq.cpp
@@ -119,9 +119,6 @@ void MidiSeq::processMsg(const ThreadMsg* m)
case MusECore::SEQM_REMOVE_PART:
MusEGlobal::song->cmdRemovePart((Part*)msg->p1);
break;
- case MusECore::SEQM_CHANGE_PART:
- MusEGlobal::song->cmdChangePart((Part*)msg->p1, (Part*)msg->p2, msg->a, msg->b);
- break;
case MusECore::SEQM_SET_TRACK_OUT_CHAN:
diff --git a/muse2/muse/part.cpp b/muse2/muse/part.cpp
index c530b1f3..10c7f201 100644
--- a/muse2/muse/part.cpp
+++ b/muse2/muse/part.cpp
@@ -372,8 +372,6 @@ void addPortCtrlEvents(Event& event, Part* part, bool doClones)
{
// Traverse and process the clone chain ring until we arrive at the same part again.
// The loop is a safety net.
- // Update: Due to the varying calls, and order of, incARefcount, (msg)ChangePart, replaceClone, and remove/addPortCtrlEvents,
- // we can not rely on the reference count as a safety net in these routines. We will just have to trust the clone chain.
Part* p = part;
while(1)
{
@@ -434,8 +432,6 @@ void addPortCtrlEvents(Part* part, bool doClones)
{
// Traverse and process the clone chain ring until we arrive at the same part again.
// The loop is a safety net.
- // Update: Due to the varying calls, and order of, incARefcount, (msg)ChangePart, replaceClone, and remove/addPortCtrlEvents,
- // we can not rely on the reference count as a safety net in these routines. We will just have to trust the clone chain.
Part* p = part;
while(1)
{
@@ -499,8 +495,6 @@ void removePortCtrlEvents(Event& event, Part* part, bool doClones)
{
// Traverse and process the clone chain ring until we arrive at the same part again.
// The loop is a safety net.
- // Update: Due to the varying calls, and order of, incARefcount, (msg)ChangePart, replaceClone, and remove/addPortCtrlEvents,
- // we can not rely on the reference count as a safety net in these routines. We will just have to trust the clone chain.
Part* p = part;
while(1)
{
@@ -555,8 +549,6 @@ void removePortCtrlEvents(Part* part, bool doClones)
{
// Traverse and process the clone chain ring until we arrive at the same part again.
// The loop is a safety net.
- // Update: Due to the varying calls, and order of, incARefcount, (msg)ChangePart, replaceClone, and remove/addPortCtrlEvents,
- // we can not rely on the reference count as a safety net in these routines. We will just have to trust the clone chain.
Part* p = part;
while(1)
{
@@ -850,6 +842,10 @@ void Song::cmdResizePart(Track* track, Part* oPart, unsigned int len, bool doClo
EventList* el = nPart->events();
unsigned new_partlength = MusEGlobal::tempomap.deltaTick2frame(oPart->tick(), oPart->tick() + len);
+ // TODO FINDMICH FIXME this is totally broken. we don't want to remove events just because they're beyond end-of-part.
+ // we also don't want to auto-resize the last event.
+
+ /*
// If new nr of frames is less than previous what can happen is:
// - 0 or more events are beginning after the new final position. Those are removed from the part
// - The last event begins before new final position and ends after it. If so, it will be resized to end at new part length
@@ -865,7 +861,7 @@ void Song::cmdResizePart(Track* track, Part* oPart, unsigned int len, bool doClo
}
nPart->setLenFrame(new_partlength);
// Do not do port controller values and clone parts.
- operations.push_back(UndoOp(UndoOp::ModifyPart, oPart, nPart, false, false));
+ operations.push_back(UndoOp(UndoOp::Modify***Part, oPart, nPart, false, false));
MusEGlobal::song->applyOperationGroup(operations);
}
@@ -890,9 +886,9 @@ void Song::cmdResizePart(Track* track, Part* oPart, unsigned int len, bool doClo
nPart->setLenFrame(new_partlength);
// Do not do port controller values and clone parts.
- operations.push_back(UndoOp(UndoOp::ModifyPart, oPart, nPart, false, false));
+ operations.push_back(UndoOp(UndoOp::Modify***Part, oPart, nPart, false, false));
MusEGlobal::song->applyOperationGroup(operations);
- }
+ } */
}
break;
case Track::MIDI:
@@ -907,10 +903,8 @@ void Song::cmdResizePart(Track* track, Part* oPart, unsigned int len, bool doClo
{
if (part_it->lenTick()==orig_len)
{
- MidiPart* newPart = new MidiPart(*part_it);
- newPart->setLenTick(len);
// Do port controller values but not clone parts.
- operations.push_back(UndoOp(UndoOp::ModifyPart, part_it, newPart, true, false));
+ operations.push_back(UndoOp(UndoOp::ModifyPartLength, part_it, part_it->lenTick(), len, true, false));
}
part_it=(MidiPart*)part_it->nextClone();
@@ -1032,45 +1026,23 @@ void Song::cmdSplitPart(Track* track, Part* part, int tick)
Part* p2;
track->splitPart(part, tick, p1, p2);
- //MusEGlobal::song->informAboutNewParts(part, p1); // is unneccessary because of ChangePart below
+ MusEGlobal::song->informAboutNewParts(part, p1);
MusEGlobal::song->informAboutNewParts(part, p2);
- startUndo();
- // Indicate no undo, and do port controller values but not clone parts.
- MusEGlobal::audio->msgChangePart(part, p1, false, true, false);
- MusEGlobal::audio->msgAddPart(p2, false);
- endUndo(SC_TRACK_MODIFIED | SC_PART_MODIFIED | SC_PART_INSERTED);
+ Undo operations;
+ operations.push_back(UndoOp(UndoOp::DeletePart, part));
+ operations.push_back(UndoOp(UndoOp::AddPart, p1));
+ operations.push_back(UndoOp(UndoOp::AddPart, p2));
+ applyOperationGroup(operations);
}
-//---------------------------------------------------------
-// changePart
-//---------------------------------------------------------
-
-void Song::changePart(Part* oPart, Part* nPart)
- {
- nPart->setSn(oPart->sn());
-
- Track* oTrack = oPart->track();
- Track* nTrack = nPart->track();
-
- oTrack->parts()->remove(oPart);
- nTrack->parts()->add(nPart);
-
-
- // Added by T356.
- // adjust song len:
- unsigned epos = nPart->tick() + nPart->lenTick();
- if (epos > len())
- _len = epos;
-
- }
//---------------------------------------------------------
// cmdGluePart
//---------------------------------------------------------
void Song::cmdGluePart(Track* track, Part* oPart)
- {
+ { /* disabled for now, to be deleted
// p3.3.54
if(track->type() != Track::WAVE && !track->isMidiTrack())
return;
@@ -1126,8 +1098,8 @@ void Song::cmdGluePart(Track* track, Part* oPart)
startUndo();
MusEGlobal::audio->msgRemovePart(nextPart, false);
// Indicate no undo, and do port controller values but not clone parts.
- MusEGlobal::audio->msgChangePart(oPart, nPart, false, true, false);
- endUndo(SC_PART_MODIFIED | SC_PART_REMOVED);
+ MusEGlobal::audio->msgChange***Part(oPart, nPart, false, true, false);
+ endUndo(SC_PART_MODIFIED | SC_PART_REMOVED); */
}
//---------------------------------------------------------
diff --git a/muse2/muse/seqmsg.cpp b/muse2/muse/seqmsg.cpp
index fcffc332..61714b98 100644
--- a/muse2/muse/seqmsg.cpp
+++ b/muse2/muse/seqmsg.cpp
@@ -923,21 +923,6 @@ bool Song::msgRemoveParts()
}
//---------------------------------------------------------
-// msgChangePart
-//---------------------------------------------------------
-
-void Audio::msgChangePart(Part* oldPart, Part* newPart, bool doUndoFlag, bool doCtrls, bool doClones)
- {
- AudioMsg msg;
- msg.id = SEQM_CHANGE_PART;
- msg.p1 = oldPart;
- msg.p2 = newPart;
- msg.a = doCtrls;
- msg.b = doClones;
- sendMessage(&msg, doUndoFlag);
- }
-
-//---------------------------------------------------------
// msgAddEvent
//---------------------------------------------------------
diff --git a/muse2/muse/song.cpp b/muse2/muse/song.cpp
index 8a7bf39f..d457cb1d 100644
--- a/muse2/muse/song.cpp
+++ b/muse2/muse/song.cpp
@@ -886,42 +886,23 @@ void Song::cmdAddRecordedEvents(MidiTrack* mt, EventList* events, unsigned start
// Round the end up (again) using the Arranger part snap raster value.
endTick = AL::sigmap.raster2(endTick, arrangerRaster());
-
- removePortCtrlEvents(part, false); // Remove all of the part's port controller values. Don't do clone parts.
-
- // Clone the part. This doesn't increment aref count, and doesn't chain clones.
- // It also gives the new part a new serial number, but it is
- // overwritten with the old one by Song::changePart(), below.
- Part* newPart = part->clone();
-
- newPart->setLenTick(endTick); // Set the new part's length.
- changePart(part, newPart); // Change the part.
-
- part->events()->incARef(-1); // Manually adjust reference counts. HACK!
- newPart->events()->incARef(1);
-
- replaceClone(part, newPart); // Replace the part in the clone chain with the new part.
-
- // Now add all of the new part's port controller values. Indicate do not do clone parts.
- addPortCtrlEvents(newPart, false);
-
// Create an undo op. Indicate do port controller values but not clone parts.
- addUndo(UndoOp(UndoOp::ModifyPart, part, newPart, true, false));
+ addUndo(UndoOp(UndoOp::ModifyPartLength, part, part->lenTick(), endTick, true, false)); // FIXME XTICKS! FINDMICHJETZT!
updateFlags |= SC_PART_MODIFIED;
if (_recMode == REC_REPLACE)
{
- iEvent si = newPart->events()->lower_bound(startTick - newPart->tick());
- iEvent ei = newPart->events()->lower_bound(newPart->endTick() - newPart->tick());
+ iEvent si = part->events()->lower_bound(startTick - part->tick());
+ iEvent ei = part->events()->lower_bound(part->endTick() - part->tick());
for (iEvent i = si; i != ei; ++i)
{
Event event = i->second;
// Indicate do port controller values and clone parts.
- addUndo(UndoOp(UndoOp::DeleteEvent, event, newPart, true, true));
+ addUndo(UndoOp(UndoOp::DeleteEvent, event, part, true, true));
// Remove the event from the new part's port controller values, and do all clone parts.
- removePortCtrlEvents(event, newPart, true);
+ removePortCtrlEvents(event, part, true);
}
- newPart->events()->erase(si, ei);
+ part->events()->erase(si, ei);
}
for (iEvent i = s; i != e; ++i) {
@@ -929,13 +910,13 @@ void Song::cmdAddRecordedEvents(MidiTrack* mt, EventList* events, unsigned start
event.setTick(event.tick() - partTick);
Event e;
// Create an undo op. Indicate do port controller values and clone parts.
- addUndo(UndoOp(UndoOp::AddEvent, e, event, newPart, true, true));
+ addUndo(UndoOp(UndoOp::AddEvent, e, event, part, true, true));
- if(newPart->events()->find(event) == newPart->events()->end())
- newPart->events()->add(event);
+ if(part->events()->find(event) == part->events()->end())
+ part->events()->add(event);
// Add the event to the new part's port controller values, and do all clone parts.
- addPortCtrlEvents(event, newPart, true);
+ addPortCtrlEvents(event, part, true);
}
}
else {
@@ -1886,7 +1867,6 @@ void Song::processMsg(AudioMsg* msg)
updateFlags = SC_EVENT_MODIFIED;
break;
- // Moved here from MidiSeq::processMsg p4.0.34
case SEQM_ADD_TRACK:
insertTrack2(msg->track, msg->ival);
break;
@@ -1899,9 +1879,6 @@ void Song::processMsg(AudioMsg* msg)
case SEQM_REMOVE_PART:
cmdRemovePart((Part*)msg->p1);
break;
- case SEQM_CHANGE_PART:
- cmdChangePart((Part*)msg->p1, (Part*)msg->p2, msg->a, msg->b);
- break;
case SEQM_ADD_TEMPO:
addUndo(UndoOp(UndoOp::AddTempo, msg->a, msg->b));
@@ -1980,32 +1957,6 @@ void Song::cmdRemovePart(Part* part)
}
//---------------------------------------------------------
-// cmdChangePart
-//---------------------------------------------------------
-
-void Song::cmdChangePart(Part* oldPart, Part* newPart, bool doCtrls, bool doClones)
- {
- if(doCtrls)
- removePortCtrlEvents(oldPart, doClones);
-
- changePart(oldPart, newPart);
-
- addUndo(UndoOp(UndoOp::ModifyPart, oldPart, newPart, doCtrls, doClones));
-
- // Changed by T356. Do not decrement ref count if the new part is a clone of the old part, since the event list
- // will still be active.
- if(oldPart->cevents() != newPart->cevents())
- oldPart->events()->incARef(-1);
-
- replaceClone(oldPart, newPart);
-
- if(doCtrls)
- addPortCtrlEvents(newPart, doClones);
-
- updateFlags = SC_PART_MODIFIED;
- }
-
-//---------------------------------------------------------
// panic
//---------------------------------------------------------
diff --git a/muse2/muse/song.h b/muse2/muse/song.h
index f6b1403d..909e54fc 100644
--- a/muse2/muse/song.h
+++ b/muse2/muse/song.h
@@ -298,12 +298,10 @@ class Song : public QObject {
void addPart(Part* part);
void removePart(Part* part);
- void changePart(Part*, Part*);
PartList* getSelectedMidiParts() const;
PartList* getSelectedWaveParts() const;
bool msgRemoveParts();
- void cmdChangePart(Part* oldPart, Part* newPart, bool doCtrls, bool doClones);
void cmdRemovePart(Part* part);
void cmdAddPart(Part* part);
int arrangerRaster() { return _arrangerRaster; } // Used by Song::cmdAddRecordedWave to snap new wave parts
diff --git a/muse2/muse/structure.cpp b/muse2/muse/structure.cpp
index 65489cac..ad22b8d3 100644
--- a/muse2/muse/structure.cpp
+++ b/muse2/muse/structure.cpp
@@ -5,6 +5,7 @@
//
// (C) Copyright 1999-2004 Werner Schweer (ws@seh.de)
// (C) Copyright 2011 Robert Jonsson (rj@spamatica.se)
+// (C) Copyright 2013 Florian Jung (flo93@sourceforge.net)
//
// This program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public License
@@ -161,19 +162,15 @@ void globalCut(bool onlySelectedTracks)
else if ((t < lpos) && ((t+l) > lpos) && ((t+l) <= rpos)) {
// remove part tail
int len = lpos - t;
- Part *nPart;
- if (track->isMidiTrack())
- nPart = new MidiPart(*(MidiPart*)part);
- else
- nPart = new WavePart(*(WavePart*)part);
-
- nPart->setLenTick(len);
- // cut Events in nPart
- EventList* el = nPart->events();
- for (iEvent ie = el->lower_bound(len); ie != el->end(); ++ie)
- operations.push_back(UndoOp(UndoOp::DeleteEvent,ie->second, nPart, false, false));
-
- operations.push_back(UndoOp(UndoOp::ModifyPart,part, nPart, true, true));
+
+ if (part->nextClone()==part) // no clones
+ {
+ // cut Events
+ EventList* el = part->events();
+ for (iEvent ie = el->lower_bound(len); ie != el->end(); ++ie)
+ operations.push_back(UndoOp(UndoOp::DeleteEvent,ie->second, part, false, false));
+ }
+ operations.push_back(UndoOp(UndoOp::ModifyPartLength, part, part->lenTick(), len, true, true));
}
else if ((t < lpos) && ((t+l) > lpos) && ((t+l) > rpos)) {
//----------------------
@@ -190,8 +187,9 @@ void globalCut(bool onlySelectedTracks)
p1->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it so we must decrement it first :/
p3->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it so we must decrement it first :/
- // Indicate no undo, and do port controller values and clone parts.
- operations.push_back(UndoOp(UndoOp::ModifyPart,part, p1, true, true));
+ MusEGlobal::song->informAboutNewParts(part,p1,p3);
+ operations.push_back(UndoOp(UndoOp::DeletePart,part));
+ operations.push_back(UndoOp(UndoOp::AddPart,p1));
operations.push_back(UndoOp(UndoOp::AddPart,p3));
}
else if ((t >= lpos) && (t < rpos) && (t+l) > rpos) {
@@ -203,19 +201,15 @@ void globalCut(bool onlySelectedTracks)
delete p1;
p2->setTick(lpos);
p2->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it so we must decrement it first :/
- operations.push_back(UndoOp(UndoOp::ModifyPart,part, p2, true, true));
+
+ MusEGlobal::song->informAboutNewParts(part,p2);
+ operations.push_back(UndoOp(UndoOp::DeletePart,part));
+ operations.push_back(UndoOp(UndoOp::AddPart,p2));
}
else if (t >= rpos) {
// move part to the left
- Part *nPart;
- if (track->isMidiTrack())
- nPart = new MidiPart(*(MidiPart*)part);
- else
- nPart = new WavePart(*(WavePart*)part);
int nt = part->tick();
- nPart->setTick(nt - (rpos -lpos));
- // Indicate no undo, and do port controller values but not clone parts.
- operations.push_back(UndoOp(UndoOp::ModifyPart,part, nPart, true, false));
+ operations.push_back(UndoOp(UndoOp::ModifyPartTick,part,part->tick(), nt - (rpos -lpos) ));
}
}
}
@@ -268,17 +262,13 @@ Undo movePartsTotheRight(unsigned int startTicks, int moveTicks, bool only_selec
p2->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it so we must decrement it first :/
p1->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it so we must decrement it first :/
- operations.push_back(UndoOp(UndoOp::ModifyPart, part, p1, true, true));
+ MusEGlobal::song->informAboutNewParts(part,p1,p2);
+ operations.push_back(UndoOp(UndoOp::DeletePart, part));
+ operations.push_back(UndoOp(UndoOp::AddPart, p1));
operations.push_back(UndoOp(UndoOp::AddPart, p2));
}
else if (t >= startTicks) {
- Part *nPart;
- if (track->isMidiTrack())
- nPart = new MidiPart(*(MidiPart*)part);
- else
- nPart = new WavePart(*(WavePart*)part);
- nPart->setTick(t + moveTicks);
- operations.push_back(UndoOp(UndoOp::ModifyPart, part, nPart, true, false));
+ operations.push_back(UndoOp(UndoOp::ModifyPartTick, part, part->tick(), t + moveTicks));
}
}
}
@@ -323,19 +313,20 @@ Undo partSplitter(unsigned int pos, bool onlySelectedTracks)
p1->events()->incARef(-1); // the later MusEGlobal::song->applyOperationGroup() will increment it
p2->events()->incARef(-1); // so we must decrement it first :/
- //MusEGlobal::song->informAboutNewParts(part, p1); // is unneccessary because of ModifyPart
+ MusEGlobal::song->informAboutNewParts(part, p1);
MusEGlobal::song->informAboutNewParts(part, p2);
- operations.push_back(UndoOp(UndoOp::ModifyPart,part, p1, true, false));
+ operations.push_back(UndoOp(UndoOp::DeletePart,part));
+ operations.push_back(UndoOp(UndoOp::AddPart,p1));
operations.push_back(UndoOp(UndoOp::AddPart,p2));
if (MusEGlobal::debugMsg)
{
printf("in partSplitter: part1 %d\n",p1->events()->refCount());
printf("in partSplitter: part2 %d\n",p2->events()->refCount());
- }
- break;
}
+ break;
}
}
+ }
return operations;
}
diff --git a/muse2/muse/undo.cpp b/muse2/muse/undo.cpp
index fc6fc1d8..924ba745 100644
--- a/muse2/muse/undo.cpp
+++ b/muse2/muse/undo.cpp
@@ -50,7 +50,7 @@ const char* UndoOp::typeName()
{
static const char* name[] = {
"AddTrack", "DeleteTrack",
- "AddPart", "DeletePart", "ModifyPart",
+ "AddPart", "DeletePart", "ModifyPartTick", "ModifyPartLength", "ModifyPartLengthFrames", "ModifyPartName",
"AddEvent", "DeleteEvent", "ModifyEvent",
"AddTempo", "DeleteTempo",
"AddSig", "DeleteSig",
@@ -77,7 +77,10 @@ void UndoOp::dump()
break;
case AddPart:
case DeletePart:
- case ModifyPart:
+ case ModifyPartTick:
+ case ModifyPartLength:
+ case ModifyPartLengthFrames:
+ case ModifyPartName:
break;
case AddEvent:
case DeleteEvent:
@@ -136,11 +139,7 @@ void UndoList::clearDelete()
break;
case UndoOp::DeletePart:
- delete i->oPart;
- break;
-
- case UndoOp::ModifyPart:
- delete i->oPart;
+ delete i->part;
break;
case UndoOp::ModifyMarker:
@@ -176,12 +175,9 @@ void UndoList::clearDelete()
break;
case UndoOp::AddPart:
- delete i->oPart;
+ delete i->part;
break;
- case UndoOp::ModifyPart:
- delete i->nPart;
- break;
case UndoOp::ModifyMarker:
if (i->realMarker)
delete i->realMarker;
@@ -295,12 +291,12 @@ void cleanOperationGroup(Undo& group)
else
processed_tracks.insert(op->track);
}
- else if ((op->type==UndoOp::ModifyPart) || (op->type==UndoOp::DeletePart))
+ else if (op->type==UndoOp::DeletePart)
{
- if (processed_parts.find(op->oPart)!=processed_parts.end())
+ if (processed_parts.find(op->part)!=processed_parts.end())
group.erase(op);
else
- processed_parts.insert(op->oPart);
+ processed_parts.insert(op->part);
}
op=op_;
@@ -370,28 +366,33 @@ void Song::doUndo2()
break;
case UndoOp::AddPart:
{
- Part* part = i->oPart;
+ Part* part = i->part;
removePart(part);
updateFlags |= SC_PART_REMOVED;
- i->oPart->events()->incARef(-1);
- unchainClone(i->oPart);
+ i->part->events()->incARef(-1);
+ unchainClone(i->part);
}
break;
case UndoOp::DeletePart:
- addPart(i->oPart);
+ addPart(i->part);
updateFlags |= SC_PART_INSERTED;
- i->oPart->events()->incARef(1);
- chainClone(i->oPart);
+ i->part->events()->incARef(1);
+ chainClone(i->part);
break;
- case UndoOp::ModifyPart:
- if(i->doCtrls)
- removePortCtrlEvents(i->nPart, i->doClones);
- changePart(i->nPart, i->oPart);
- i->nPart->events()->incARef(-1);
- i->oPart->events()->incARef(1);
- replaceClone(i->nPart, i->oPart);
- if(i->doCtrls)
- addPortCtrlEvents(i->oPart, i->doClones);
+ case UndoOp::ModifyPartName:
+ i->part->setName(i->_oldName);
+ updateFlags |= SC_PART_MODIFIED;
+ break;
+ case UndoOp::ModifyPartTick: // TODO FIXME (?) do port ctrls/clones?
+ i->part->setTick(i->old_partlen_or_tick);
+ updateFlags |= SC_PART_MODIFIED;
+ break;
+ case UndoOp::ModifyPartLength: // TODO FIXME (?) do port ctrls/clones?
+ i->part->setLenTick(i->old_partlen_or_tick);
+ updateFlags |= SC_PART_MODIFIED;
+ break;
+ case UndoOp::ModifyPartLengthFrames: // TODO FIXME FINDMICH frames deprecated! do port ctrls/clones?
+ i->part->setLenFrame(i->old_partlen_or_tick);
updateFlags |= SC_PART_MODIFIED;
break;
case UndoOp::AddEvent:
@@ -484,26 +485,31 @@ void Song::doRedo2()
}
break;
case UndoOp::AddPart:
- addPart(i->oPart);
+ addPart(i->part);
updateFlags |= SC_PART_INSERTED;
- i->oPart->events()->incARef(1);
- chainClone(i->oPart);
+ i->part->events()->incARef(1);
+ chainClone(i->part);
break;
case UndoOp::DeletePart:
- removePart(i->oPart);
+ removePart(i->part);
updateFlags |= SC_PART_REMOVED;
- i->oPart->events()->incARef(-1);
- unchainClone(i->oPart);
+ i->part->events()->incARef(-1);
+ unchainClone(i->part);
break;
- case UndoOp::ModifyPart:
- if(i->doCtrls)
- removePortCtrlEvents(i->oPart, i->doClones);
- changePart(i->oPart, i->nPart);
- i->nPart->events()->incARef(1);
- i->oPart->events()->incARef(-1);
- replaceClone(i->oPart, i->nPart);
- if(i->doCtrls)
- addPortCtrlEvents(i->nPart, i->doClones);
+ case UndoOp::ModifyPartName:
+ i->part->setName(i->_newName);
+ updateFlags |= SC_PART_MODIFIED;
+ break;
+ case UndoOp::ModifyPartTick: // TODO FIXME (?) do port ctrls/clones?
+ i->part->setTick(i->new_partlen_or_tick);
+ updateFlags |= SC_PART_MODIFIED;
+ break;
+ case UndoOp::ModifyPartLength: // TODO FIXME (?) do port ctrls/clones?
+ i->part->setLenTick(i->new_partlen_or_tick);
+ updateFlags |= SC_PART_MODIFIED;
+ break;
+ case UndoOp::ModifyPartLengthFrames: // TODO FIXME FINDMICH frames deprecated! do port ctrls/clones?
+ i->part->setLenFrame(i->new_partlen_or_tick);
updateFlags |= SC_PART_MODIFIED;
break;
case UndoOp::AddEvent:
@@ -590,10 +596,12 @@ UndoOp::UndoOp(UndoType type_, int n, Track* track_)
track = track_;
}
-UndoOp::UndoOp(UndoType type_, Part* part)
+UndoOp::UndoOp(UndoType type_, Part* part, unsigned old_len_or_tick, unsigned new_len_or_tick, bool, bool)
{
type = type_;
- oPart = part;
+ part = part;
+ old_partlen_or_tick=old_len_or_tick;
+ new_partlen_or_tick=new_len_or_tick;
}
UndoOp::UndoOp(UndoType type_, Event& oev, Event& nev, Part* part_, bool doCtrls_, bool doClones_)
@@ -615,15 +623,6 @@ UndoOp::UndoOp(UndoType type_, Event& nev, Part* part_, bool doCtrls_, bool doCl
doClones = doClones_;
}
-UndoOp::UndoOp(UndoType type_, Part* oPart_, Part* nPart_, bool doCtrls_, bool doClones_)
- {
- type = type_;
- oPart = oPart_;
- nPart = nPart_;
- doCtrls = doCtrls_;
- doClones = doClones_;
- }
-
UndoOp::UndoOp(UndoType type_, int c, int ctrl_, int ov, int nv)
{
type = type_;
@@ -649,10 +648,20 @@ UndoOp::UndoOp(UndoType type_, const char* changedFile, const char* changeData,
endframe = endframe_;
}
+UndoOp::UndoOp(UndoOp::UndoType type_, Part* part_, const char* old_name, const char* new_name)
+{
+ type=type_;
+ part=part_;
+ _oldName = new char[strlen(old_name) + 1];
+ _newName = new char[strlen(new_name) + 1];
+ strcpy(_oldName, old_name);
+ strcpy(_newName, new_name);
+}
+
UndoOp::UndoOp(UndoOp::UndoType type_, Track* track_, const char* old_name, const char* new_name)
{
type = type_;
- _renamedTrack = track_;
+ track = track_;
_oldName = new char[strlen(old_name) + 1];
_newName = new char[strlen(new_name) + 1];
strcpy(_oldName, old_name);
@@ -727,7 +736,7 @@ bool Song::doUndo1()
break;
case UndoOp::ModifyTrackName:
- i->_renamedTrack->setName(i->_oldName);
+ i->track->setName(i->_oldName);
updateFlags |= SC_TRACK_MODIFIED;
break;
case UndoOp::ModifyClip:
@@ -851,7 +860,7 @@ bool Song::doRedo1()
removeTrack1(i->track);
break;
case UndoOp::ModifyTrackName:
- i->_renamedTrack->setName(i->_newName);
+ i->track->setName(i->_newName);
updateFlags |= SC_TRACK_MODIFIED;
break;
case UndoOp::ModifyClip:
diff --git a/muse2/muse/undo.h b/muse2/muse/undo.h
index 2f582d8e..4fded825 100644
--- a/muse2/muse/undo.h
+++ b/muse2/muse/undo.h
@@ -46,7 +46,7 @@ extern std::list<QString> temporaryWavFiles; //!< Used for storing all tmp-files
struct UndoOp {
enum UndoType {
AddTrack, DeleteTrack,
- AddPart, DeletePart, ModifyPart,
+ AddPart, DeletePart, ModifyPartTick, ModifyPartLength, ModifyPartLengthFrames, /* FINDMICH FIXME frames are to be deprecated */ ModifyPartName,
AddEvent, DeleteEvent, ModifyEvent,
AddTempo, DeleteTempo,
AddSig, DeleteSig,
@@ -71,11 +71,9 @@ struct UndoOp {
int trackno;
};
struct {
- Part* oPart;
- Part* nPart;
- };
- struct {
- Part* part; // this part is only relevant for EVENT operations, NOT for part ops!
+ Part* part;
+ unsigned old_partlen_or_tick; // FIXME FINDMICHJETZT XTicks!!
+ unsigned new_partlen_or_tick;
};
struct {
int channel;
@@ -94,16 +92,14 @@ struct UndoOp {
Marker* copyMarker;
};
struct {
- Track* _renamedTrack;
- char* _oldName;
- char* _newName;
- };
- struct {
Track* _propertyTrack;
int _oldPropValue;
int _newPropValue;
};
};
+
+ char* _oldName;
+ char* _newName;
Event oEvent;
Event nEvent;
bool doCtrls;
@@ -115,10 +111,11 @@ struct UndoOp {
UndoOp();
UndoOp(UndoType type, int a, int b, int c=0);
UndoOp(UndoType type, int n, Track* track);
- UndoOp(UndoType type, Part* part);
+ UndoOp(UndoType type, 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!!
+ UndoOp(UndoType type, Part* part, const char* old_name, const char* new_name);
UndoOp(UndoType type, Event& oev, Event& nev, Part* part, bool doCtrls, bool doClones);
UndoOp(UndoType type, Event& nev, Part* part, bool doCtrls, bool doClones);
- UndoOp(UndoType type, Part* oPart, Part* nPart, bool doCtrls, bool doClones);
+ UndoOp(UndoType type, Part* part, unsigned tick, bool doCtrls, bool doClones); // FIXME FINDMICHJETZT XTicks!
UndoOp(UndoType type, int c, int ctrl, int ov, int nv);
UndoOp(UndoType type, const char* changedFile, const char* changeData, int startframe, int endframe);
UndoOp(UndoType type, Marker* copyMarker, Marker* realMarker);