mirror of
https://github.com/microtherion/VocalEasel.git
synced 2024-12-22 11:14:00 +00:00
Added undo support
This commit is contained in:
parent
94f23e92f2
commit
9af760d1dc
|
@ -8,6 +8,7 @@
|
|||
|
||||
#import "VLModel.h"
|
||||
#import <Cocoa/Cocoa.h>
|
||||
#import "VLKeyValueUndo.h"
|
||||
|
||||
@class VLSheetWindow;
|
||||
@class VLPDFWindow;
|
||||
|
@ -29,6 +30,7 @@
|
|||
VLSheetWindow * sheetWin;
|
||||
VLLogWindow * logWin;
|
||||
VLPDFWindow * pdfWin;
|
||||
VLKeyValueUndo* undo;
|
||||
}
|
||||
|
||||
- (VLSong *) song;
|
||||
|
@ -49,6 +51,8 @@
|
|||
- (NSString *) baseName;
|
||||
- (NSURL *) fileURLWithExtension:(NSString*)extension;
|
||||
- (NSTask *) taskWithLaunchPath:(NSString *)path arguments:(NSArray *)args;
|
||||
- (void) willChangeSong;
|
||||
- (void) didChangeSong;
|
||||
|
||||
@end
|
||||
|
||||
|
|
|
@ -16,6 +16,43 @@
|
|||
#import "VLSheetWindow.h"
|
||||
#import "VLSoundOut.h"
|
||||
|
||||
@interface VLSongWrapper : NSObject {
|
||||
VLSong * wrappedSong;
|
||||
}
|
||||
|
||||
+ (VLSongWrapper *)wrapperWithSong:(VLSong *)song;
|
||||
- (VLSong *)song;
|
||||
|
||||
@end
|
||||
|
||||
@implementation VLSongWrapper
|
||||
|
||||
- (id)initWithSong:(VLSong *)song
|
||||
{
|
||||
if (self = [super init])
|
||||
wrappedSong = new VLSong(*song);
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void) dealloc
|
||||
{
|
||||
delete wrappedSong;
|
||||
|
||||
[super dealloc];
|
||||
}
|
||||
|
||||
+ (VLSongWrapper *)wrapperWithSong:(VLSong *)song
|
||||
{
|
||||
return [[[VLSongWrapper alloc] initWithSong:song] autorelease];
|
||||
}
|
||||
|
||||
- (VLSong *)song
|
||||
{
|
||||
return wrappedSong;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation VLDocument
|
||||
|
||||
- (id)init
|
||||
|
@ -35,6 +72,17 @@
|
|||
logWin = nil;
|
||||
tmpPath = nil;
|
||||
vcsWrapper = nil;
|
||||
[self setHasUndoManager:YES];
|
||||
undo =
|
||||
[[VLKeyValueUndo alloc] initWithOwner:self
|
||||
keysAndNames: [NSDictionary dictionaryWithObjectsAndKeys:
|
||||
@"", @"songTitle",
|
||||
@"", @"songLyricist",
|
||||
@"", @"songComposer",
|
||||
@"", @"songArranger",
|
||||
@"", @"songGroove",
|
||||
@"", @"songTempo",
|
||||
nil]];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
@ -49,6 +97,7 @@
|
|||
[songComposer release];
|
||||
[songArranger release];
|
||||
[vcsWrapper release];
|
||||
[undo release];
|
||||
|
||||
if (tmpPath) {
|
||||
[[NSFileManager defaultManager] removeFileAtPath:tmpPath handler:nil];
|
||||
|
@ -119,9 +168,11 @@
|
|||
|
||||
- (void) setKey:(int)key transpose:(BOOL)transpose
|
||||
{
|
||||
[self willChangeSong];
|
||||
|
||||
VLProperties & prop = song->fProperties.front();
|
||||
|
||||
if (transpose)
|
||||
if (transpose)
|
||||
song->Transpose((7*((key>>8)-prop.fKey) % 12));
|
||||
|
||||
prop.fKey = key >> 8;
|
||||
|
@ -139,6 +190,8 @@
|
|||
|
||||
- (void) setTimeNum:(int)num denom:(int)denom
|
||||
{
|
||||
[self willChangeSong];
|
||||
|
||||
VLProperties & prop = song->fProperties.front();
|
||||
|
||||
prop.fTime = VLFraction(num, denom);
|
||||
|
@ -155,6 +208,8 @@
|
|||
|
||||
- (void) setDivisions:(int)divisions
|
||||
{
|
||||
[self willChangeSong];
|
||||
|
||||
VLProperties & prop = song->fProperties.front();
|
||||
|
||||
prop.fDivisions = divisions;
|
||||
|
@ -328,4 +383,31 @@
|
|||
[[self logWin] showWindow:sender];
|
||||
}
|
||||
|
||||
- (void) willChangeSong
|
||||
{
|
||||
[self willChangeValueForKey:@"song"];
|
||||
[[self undoManager] registerUndoWithTarget:self
|
||||
selector:@selector(restoreSong:)
|
||||
object:[VLSongWrapper wrapperWithSong:song]];
|
||||
}
|
||||
|
||||
- (void) didChangeSong
|
||||
{
|
||||
[self didChangeValueForKey:@"song"];
|
||||
[self updateChangeCount:NSChangeDone];
|
||||
}
|
||||
|
||||
- (void) restoreSong:(VLSongWrapper *)savedSong
|
||||
{
|
||||
[self willChangeSong];
|
||||
[self willChangeValueForKey:@"songKey"];
|
||||
[self willChangeValueForKey:@"songTime"];
|
||||
[self willChangeValueForKey:@"songDivisions"];
|
||||
song->swap(*[savedSong song]);
|
||||
[self didChangeValueForKey:@"songKey"];
|
||||
[self didChangeValueForKey:@"songTime"];
|
||||
[self didChangeValueForKey:@"songDivisions"];
|
||||
[self didChangeSong];
|
||||
}
|
||||
|
||||
@end
|
||||
|
|
18
Sources/VLKeyValueUndo.h
Normal file
18
Sources/VLKeyValueUndo.h
Normal file
|
@ -0,0 +1,18 @@
|
|||
//
|
||||
// VLKeyValueUndo.h
|
||||
// Vocalese
|
||||
//
|
||||
// Created by Matthias Neeracher on 12/3/06.
|
||||
// Copyright 2006 __MyCompanyName__. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Cocoa/Cocoa.h>
|
||||
|
||||
@interface VLKeyValueUndo : NSObject {
|
||||
id owner;
|
||||
NSDictionary * keysAndNames;
|
||||
}
|
||||
|
||||
- (id)initWithOwner:(id)owner keysAndNames:(NSDictionary *)keysAndNames;
|
||||
|
||||
@end
|
54
Sources/VLKeyValueUndo.mm
Normal file
54
Sources/VLKeyValueUndo.mm
Normal file
|
@ -0,0 +1,54 @@
|
|||
//
|
||||
// VLKeyValueUndo.mm
|
||||
// Vocalese
|
||||
//
|
||||
// Created by Matthias Neeracher on 12/3/06.
|
||||
// Copyright 2006 __MyCompanyName__. All rights reserved.
|
||||
//
|
||||
|
||||
#import "VLKeyValueUndo.h"
|
||||
|
||||
|
||||
@implementation VLKeyValueUndo
|
||||
|
||||
- (id)initWithOwner:(id)o keysAndNames:(NSDictionary *)kn
|
||||
{
|
||||
owner = o;
|
||||
keysAndNames = [kn retain];
|
||||
|
||||
for (NSEnumerator * e = [keysAndNames keyEnumerator];
|
||||
NSString * key = [e nextObject];
|
||||
)
|
||||
[owner addObserver:self forKeyPath:key
|
||||
options:NSKeyValueObservingOptionOld|NSKeyValueObservingOptionNew
|
||||
context:[keysAndNames objectForKey:key]];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void) dealloc
|
||||
{
|
||||
for (NSEnumerator * e = [keysAndNames keyEnumerator];
|
||||
NSString * key = [e nextObject];
|
||||
)
|
||||
[owner removeObserver:self forKeyPath:key];
|
||||
|
||||
[keysAndNames release];
|
||||
[super dealloc];
|
||||
}
|
||||
|
||||
- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
|
||||
{
|
||||
id oldVal = [change objectForKey:NSKeyValueChangeOldKey];
|
||||
id newVal = [change objectForKey:NSKeyValueChangeNewKey];
|
||||
|
||||
if (![oldVal isEqual:newVal]) {
|
||||
NSUndoManager * undo = [owner undoManager];
|
||||
NSString * name = [keysAndNames objectForKey:keyPath];
|
||||
[undo registerUndoWithTarget:owner selector:@selector(setValuesForKeysWithDictionary:)
|
||||
object: [NSDictionary dictionaryWithObjectsAndKeys: oldVal, keyPath, nil]];
|
||||
[undo setActionName: name];
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
|
@ -32,9 +32,9 @@
|
|||
for (size_t m=0; m<song->CountMeasures(); ++m) {
|
||||
sprintf(buf, "%-5d", m+1);
|
||||
mmaFile += buf;
|
||||
song->fMeasures[m].MMAChords(mmas);
|
||||
song->fMeasures[m].MMAChords(mmas, prop);
|
||||
mmaFile += mmas;
|
||||
song->fMeasures[m].MMANotes(mmas);
|
||||
song->fMeasures[m].MMANotes(mmas, prop);
|
||||
mmaFile += "\t{ " + mmas + " }\n";
|
||||
}
|
||||
|
||||
|
|
|
@ -737,11 +737,11 @@ void VLProperties::VisualNote(VLFraction at, VLFraction actualDur,
|
|||
}
|
||||
|
||||
VLMeasure::VLMeasure()
|
||||
: fProperties(0)
|
||||
: fPropIdx(0)
|
||||
{
|
||||
}
|
||||
|
||||
void VLMeasure::MMANotes(std::string & notes) const
|
||||
void VLMeasure::MMANotes(std::string & notes, const VLProperties & prop) const
|
||||
{
|
||||
VLFraction at(0);
|
||||
VLNoteList::const_iterator i = fMelody.begin();
|
||||
|
@ -750,7 +750,7 @@ void VLMeasure::MMANotes(std::string & notes) const
|
|||
notes.clear();
|
||||
for (; i!=e; ++i) {
|
||||
std::string note;
|
||||
i->MMAName(note, at, *fProperties);
|
||||
i->MMAName(note, at, prop);
|
||||
if (notes.size())
|
||||
notes += ' ';
|
||||
notes += note+';';
|
||||
|
@ -758,7 +758,7 @@ void VLMeasure::MMANotes(std::string & notes) const
|
|||
}
|
||||
}
|
||||
|
||||
void VLMeasure::MMAChords(std::string & chords) const
|
||||
void VLMeasure::MMAChords(std::string & chords, const VLProperties & prop) const
|
||||
{
|
||||
VLChordList::const_iterator i = fChords.begin();
|
||||
VLChordList::const_iterator e = fChords.end();
|
||||
|
@ -766,7 +766,7 @@ void VLMeasure::MMAChords(std::string & chords) const
|
|||
chords.clear();
|
||||
for (; i!=e; ++i) {
|
||||
std::string chord;
|
||||
i->MMAName(chord, fProperties->fKey >= 0);
|
||||
i->MMAName(chord, prop.fKey >= 0);
|
||||
if (chords.size())
|
||||
chords += ' ';
|
||||
chords += chord;
|
||||
|
@ -786,12 +786,17 @@ VLSong::VLSong()
|
|||
rchord.fDuration = 1;
|
||||
|
||||
for (int i=0; i<32; ++i) {
|
||||
fMeasures[i].fProperties = &fProperties.front();
|
||||
fMeasures[i].fChords.push_back(rchord);
|
||||
fMeasures[i].fMelody.push_back(rest);
|
||||
}
|
||||
}
|
||||
|
||||
void VLSong::swap(VLSong & other)
|
||||
{
|
||||
fProperties.swap(other.fProperties);
|
||||
fMeasures.swap(other.fMeasures);
|
||||
}
|
||||
|
||||
//
|
||||
// Deal with chords - a bit simpler
|
||||
//
|
||||
|
@ -1046,7 +1051,7 @@ void VLSong::LilypondNotes(std::string & notes) const
|
|||
|
||||
for (; i!=e; ++i) {
|
||||
std::string note;
|
||||
i->LilypondName(note, at, *fMeasures[measure].fProperties);
|
||||
i->LilypondName(note, at, fProperties[fMeasures[measure].fPropIdx]);
|
||||
at += i->fDuration;
|
||||
notes += note+" ";
|
||||
}
|
||||
|
@ -1065,7 +1070,7 @@ void VLSong::LilypondChords(std::string & chords) const
|
|||
{
|
||||
chords = "";
|
||||
for (size_t measure=0; measure<fMeasures.size(); ++measure) {
|
||||
bool useSharps = fMeasures[measure].fProperties->fKey>=0;
|
||||
bool useSharps = fProperties[fMeasures[measure].fPropIdx].fKey>=0;
|
||||
VLChordList::const_iterator i = fMeasures[measure].fChords.begin();
|
||||
VLChordList::const_iterator e = fMeasures[measure].fChords.end();
|
||||
|
||||
|
@ -1145,7 +1150,7 @@ bool VLSong::PrevWord(size_t stanza, size_t & measure, VLFraction & at)
|
|||
|
||||
return true;
|
||||
} else {
|
||||
at = meas.fProperties->fTime;
|
||||
at = fProperties[meas.fPropIdx].fTime;
|
||||
}
|
||||
} while (measure-- > 0);
|
||||
|
||||
|
|
|
@ -233,21 +233,22 @@ typedef std::list<VLChord> VLChordList;
|
|||
typedef std::list<VLLyricsNote> VLNoteList;
|
||||
|
||||
struct VLMeasure {
|
||||
VLProperties * fProperties;
|
||||
VLChordList fChords;
|
||||
VLNoteList fMelody;
|
||||
int8_t fPropIdx;
|
||||
VLChordList fChords;
|
||||
VLNoteList fMelody;
|
||||
|
||||
VLMeasure();
|
||||
|
||||
void MMANotes(std::string & notes) const;
|
||||
void MMAChords(std::string & chords) const;
|
||||
void MMANotes(std::string & notes, const VLProperties & prop) const;
|
||||
void MMAChords(std::string & chords, const VLProperties & prop) const;
|
||||
};
|
||||
|
||||
struct VLSong {
|
||||
VLSong();
|
||||
void swap(VLSong & other);
|
||||
|
||||
std::list<VLProperties> fProperties;
|
||||
std::vector<VLMeasure> fMeasures;
|
||||
std::vector<VLProperties> fProperties;
|
||||
std::vector<VLMeasure> fMeasures;
|
||||
|
||||
void AddChord(VLChord chord, size_t measure, VLFraction at);
|
||||
void AddNote(VLLyricsNote note, size_t measure, VLFraction at);
|
||||
|
|
|
@ -740,4 +740,17 @@ static int8_t sSharpAcc[] = {
|
|||
[self setScaleFactor: fDisplayScale / sqrt(sqrt(2.0))];
|
||||
}
|
||||
|
||||
- (void)awakeFromNib
|
||||
{
|
||||
[[self document] addObserver:self forKeyPath:@"song" options:0 context:nil];
|
||||
[[self document] addObserver:self forKeyPath:@"songKey" options:0 context:nil];
|
||||
}
|
||||
|
||||
- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)o change:(NSDictionary *)c context:(id)ctx
|
||||
{
|
||||
if ([keyPath isEqual:@"songKey"])
|
||||
fNeedsRecalc = kRecalc;
|
||||
[self setNeedsDisplay: YES];
|
||||
}
|
||||
|
||||
@end
|
||||
|
|
|
@ -121,10 +121,11 @@ std::string NormalizeName(NSString* rawName)
|
|||
} else {
|
||||
VLChord chord(chordName);
|
||||
VLSoundOut::Instance()->PlayChord(chord);
|
||||
|
||||
[[fView document] willChangeSong];
|
||||
fSong->AddChord(chord, fMeasure, fAt);
|
||||
[fView setNeedsDisplay:YES];
|
||||
[[fView document] didChangeSong];
|
||||
}
|
||||
[[fView document] updateChangeCount:NSChangeDone];
|
||||
}
|
||||
|
||||
- (BOOL) validValue:(NSString *)val
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
VLSong * fSong;
|
||||
size_t fStanza;
|
||||
size_t fMeasure;
|
||||
VLFraction fAt;
|
||||
VLFract fAt;
|
||||
}
|
||||
|
||||
- (VLLyricsEditable *)initWithView:(VLSheetView *)view
|
||||
|
|
|
@ -28,7 +28,9 @@
|
|||
fMeasure= measure;
|
||||
fAt = at;
|
||||
|
||||
fSong->FindWord(fStanza, fMeasure, fAt);
|
||||
VLFraction At = fAt;
|
||||
fSong->FindWord(fStanza, fMeasure, At);
|
||||
fAt = At;
|
||||
|
||||
[fView setNeedsDisplay: YES];
|
||||
|
||||
|
@ -43,7 +45,9 @@
|
|||
|
||||
- (void) setStringValue:(NSString *)val
|
||||
{
|
||||
[[fView document] willChangeSong];
|
||||
fSong->SetWord(fStanza, fMeasure, fAt, [val UTF8String]);
|
||||
[[fView document] didChangeSong];
|
||||
}
|
||||
|
||||
- (BOOL) validValue:(NSString *)val
|
||||
|
@ -53,20 +57,24 @@
|
|||
|
||||
- (void) moveToNext
|
||||
{
|
||||
if (!fSong->NextWord(fStanza, fMeasure, fAt)) {
|
||||
VLFraction at = fAt;
|
||||
if (!fSong->NextWord(fStanza, fMeasure, at)) {
|
||||
fMeasure = 0;
|
||||
fAt = 0;
|
||||
fSong->FindWord(fStanza, fMeasure, fAt);
|
||||
at = 0;
|
||||
fSong->FindWord(fStanza, fMeasure, at);
|
||||
}
|
||||
fAt = at;
|
||||
}
|
||||
|
||||
- (void) moveToPrev
|
||||
{
|
||||
if (!fSong->PrevWord(fStanza, fMeasure, fAt)) {
|
||||
VLFraction at = fAt;
|
||||
if (!fSong->PrevWord(fStanza, fMeasure, at)) {
|
||||
fMeasure = fSong->CountMeasures()-1;
|
||||
fAt = fSong->fMeasures[fMeasure].fProperties->fTime;
|
||||
fSong->PrevWord(fStanza, fMeasure, fAt);
|
||||
at = fSong->fProperties.front().fTime;
|
||||
fSong->PrevWord(fStanza, fMeasure, at);
|
||||
}
|
||||
fAt = at;
|
||||
}
|
||||
|
||||
- (void) highlightCursor
|
||||
|
|
|
@ -20,13 +20,12 @@
|
|||
if (fCursorMeasure > -1) {
|
||||
VLNote newNote(1, fClickMode==' ' ? fCursorActualPitch : VLNote::kNoPitch);
|
||||
|
||||
[[self document] willChangeSong];
|
||||
if (fClickMode == 'k')
|
||||
[self song]->DelNote(fCursorMeasure, fCursorAt);
|
||||
else
|
||||
[self song]->AddNote(VLLyricsNote(newNote), fCursorMeasure, fCursorAt);
|
||||
|
||||
[self setNeedsDisplay:YES];
|
||||
[[self document] updateChangeCount:NSChangeDone];
|
||||
[[self document] didChangeSong];
|
||||
|
||||
if (fClickMode == ' ')
|
||||
VLSoundOut::Instance()->PlayNote(newNote);
|
||||
|
@ -269,8 +268,8 @@
|
|||
VLFraction partialDur; // Actual value of note drawn
|
||||
VLFraction noteDur; // Visual value of note
|
||||
bool triplet;
|
||||
measure.fProperties->PartialNote(at, dur, &partialDur);
|
||||
measure.fProperties->VisualNote(at, partialDur, ¬eDur, &triplet);
|
||||
prop.PartialNote(at, dur, &partialDur);
|
||||
prop.VisualNote(at, partialDur, ¬eDur, &triplet);
|
||||
|
||||
if (pitch != VLNote::kNoPitch) {
|
||||
VLMusicElement accidental;
|
||||
|
|
|
@ -40,6 +40,8 @@
|
|||
95498DBD0AE3812F006B5F81 /* VLSoundSched.mm in Sources */ = {isa = PBXBuildFile; fileRef = 95498DBC0AE3812F006B5F81 /* VLSoundSched.mm */; };
|
||||
954BBD860AEDDE5300BBFD5F /* VLAppController.mm in Sources */ = {isa = PBXBuildFile; fileRef = 954BBD850AEDDE5300BBFD5F /* VLAppController.mm */; };
|
||||
954BBD9A0AEDE81500BBFD5F /* VLPitchTransformer.mm in Sources */ = {isa = PBXBuildFile; fileRef = 954BBD990AEDE81500BBFD5F /* VLPitchTransformer.mm */; };
|
||||
955CBA4E0B2366DD001CF4A1 /* VLKeyValueUndo.h in Copy MMA Library */ = {isa = PBXBuildFile; fileRef = 955CBA4C0B2366DD001CF4A1 /* VLKeyValueUndo.h */; };
|
||||
955CBA4F0B2366DD001CF4A1 /* VLKeyValueUndo.mm in Sources */ = {isa = PBXBuildFile; fileRef = 955CBA4D0B2366DD001CF4A1 /* VLKeyValueUndo.mm */; };
|
||||
955E58E5095658AB0045FDA5 /* VLModel.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 955E58E4095658AB0045FDA5 /* VLModel.cpp */; };
|
||||
955E59610957C1400045FDA5 /* TVLChord.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 955E59600957C1400045FDA5 /* TVLChord.cpp */; };
|
||||
955E59640957C15A0045FDA5 /* VLModel.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 955E58E4095658AB0045FDA5 /* VLModel.cpp */; };
|
||||
|
@ -106,6 +108,7 @@
|
|||
95009B640B0ED18700EB33A4 /* CAConditionalMacros.h in Copy MMA Library */,
|
||||
95009B650B0ED18700EB33A4 /* CAMath.h in Copy MMA Library */,
|
||||
95E299BF0B2006F5001977D2 /* VLSheetViewLyrics.h in Copy MMA Library */,
|
||||
955CBA4E0B2366DD001CF4A1 /* VLKeyValueUndo.h in Copy MMA Library */,
|
||||
);
|
||||
name = "Copy MMA Library";
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
|
@ -167,6 +170,8 @@
|
|||
954BBD850AEDDE5300BBFD5F /* VLAppController.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = VLAppController.mm; path = Sources/VLAppController.mm; sourceTree = "<group>"; };
|
||||
954BBD980AEDE81500BBFD5F /* VLPitchTransformer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = VLPitchTransformer.h; path = Sources/VLPitchTransformer.h; sourceTree = "<group>"; };
|
||||
954BBD990AEDE81500BBFD5F /* VLPitchTransformer.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = VLPitchTransformer.mm; path = Sources/VLPitchTransformer.mm; sourceTree = "<group>"; };
|
||||
955CBA4C0B2366DD001CF4A1 /* VLKeyValueUndo.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = VLKeyValueUndo.h; path = Sources/VLKeyValueUndo.h; sourceTree = "<group>"; };
|
||||
955CBA4D0B2366DD001CF4A1 /* VLKeyValueUndo.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = VLKeyValueUndo.mm; path = Sources/VLKeyValueUndo.mm; sourceTree = "<group>"; };
|
||||
955E58E3095658AB0045FDA5 /* VLModel.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = VLModel.h; path = Sources/VLModel.h; sourceTree = "<group>"; };
|
||||
955E58E4095658AB0045FDA5 /* VLModel.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = VLModel.cpp; path = Sources/VLModel.cpp; sourceTree = "<group>"; };
|
||||
955E595C0957C0FC0045FDA5 /* TVLChord */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = TVLChord; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
|
@ -356,6 +361,8 @@
|
|||
954BBD850AEDDE5300BBFD5F /* VLAppController.mm */,
|
||||
954BBD980AEDE81500BBFD5F /* VLPitchTransformer.h */,
|
||||
954BBD990AEDE81500BBFD5F /* VLPitchTransformer.mm */,
|
||||
955CBA4C0B2366DD001CF4A1 /* VLKeyValueUndo.h */,
|
||||
955CBA4D0B2366DD001CF4A1 /* VLKeyValueUndo.mm */,
|
||||
);
|
||||
name = Classes;
|
||||
sourceTree = "<group>";
|
||||
|
@ -634,6 +641,7 @@
|
|||
95009B2C0B0ECF9000EB33A4 /* CAStreamBasicDescription.cpp in Sources */,
|
||||
95009B500B0ED0BB00EB33A4 /* CADebugMacros.cpp in Sources */,
|
||||
95E299C00B2006F5001977D2 /* VLSheetViewLyrics.mm in Sources */,
|
||||
955CBA4F0B2366DD001CF4A1 /* VLKeyValueUndo.mm in Sources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
|
|
Loading…
Reference in New Issue
Block a user