File: notes.hh

package info (click to toggle)
performous 0.7.0%2Bgit20140715-2
  • links: PTS, VCS
  • area: main
  • in suites: jessie, jessie-kfreebsd
  • size: 7,900 kB
  • ctags: 3,470
  • sloc: cpp: 16,647; sh: 2,495; ansic: 2,015; python: 431; xml: 407; objc: 245; makefile: 12
file content (123 lines) | stat: -rw-r--r-- 4,156 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
#pragma once

#include <map>
#include <string>
#include <vector>

#include "color.hh"
#include "musicalscale.hh"

/// stores duration of a note
struct Duration {
	double begin, ///< beginning timestamp in seconds
	       end;   ///< ending timestamp in seconds
	Duration();
	/// create a new Duration object and initialize begin and end
	Duration(double b, double e): begin(b), end(e) {}
	/// compares begin timestamps of two Duration structs
	static bool ltBegin(Duration const& a, Duration const& b) { return a.begin < b.begin; }
	/// compares end timestamps of two Duration structs
	static bool ltEnd(Duration const& a, Duration const& b) { return a.end < b.end; }
};

typedef std::vector<Duration> Durations;
typedef std::map<int, Durations> NoteMap;

/// Sort by instrument track name
struct CompInstrumentTrack {
	bool operator()(std::string const& l, std::string const& r) const {
		// TODO: Sort other guitar tracks (coop / rhythm) properly
		return l > r;
	}
};

struct InstrumentTrack {
	// TODO: name should not be needed here (contained into the map)
	InstrumentTrack(std::string n): name(n) {}
	std::string name;
	NoteMap nm;
};

// keep these ones
typedef std::map<std::string, InstrumentTrack, CompInstrumentTrack> InstrumentTracks;
typedef std::map<std::string, InstrumentTrack const*, CompInstrumentTrack> InstrumentTracksConstPtr; // this one really needed ? can't we save only the map key for comparison ?

static inline bool isTrackInside(InstrumentTracks const& track_map, std::string const& name) {
	return track_map.find(name) != track_map.end();
}

// TODO: Make Note use Duration

/// note read from songfile
struct Note {
	Note();
	double begin, ///< begin time
	       end; ///< end time
	double phase; /// Position within a measure, [0, 1)
	// FIXME: Remove gameplay variables from here (Note should be immutable).
	/// power of note (how well it is being hit right now)
	mutable double power;
	/// which players sung well
	mutable std::vector<Color> stars;
	/// note type
	enum Type { FREESTYLE = 'F', NORMAL = ':', GOLDEN = '*', SLIDE = '+', SLEEP = '-',
	  TAP = '1', HOLDBEGIN = '2', HOLDEND = '3', ROLL = '4', MINE = 'M', LIFT = 'L'} type;
	int note; ///< MIDI pitch of the note (at the end for slide notes)
	int notePrev; ///< MIDI pitch of the previous note (should be same as note for everything but SLIDE)
	/// lyrics syllable for that note
	std::string syllable;
	/// Difference of n from note
	double diff(double n) const { return diff(note, n); }
	/// Difference of n from note, so that note + diff(note, n) is n (mod 12)
	static double diff(double note, double n);
	/// Maximum score
	double maxScore() const;
	/// The length of the time period [a,b] that falls within the note in seconds
	double clampDuration(double b, double e) const;
	/// Score when singing over time period (a, b), which needs not to be entirely within the note
	double score(double freq, double b, double e) const;
	/// How precisely the note is hit (always 1.0 for freestyle, 0..1 for others)
	double powerFactor(double note) const;
	/// Compares begin of two notes
	static bool ltBegin(Note const& a, Note const& b) { return a.begin < b.begin; }
	/// Compares end of two notes
	static bool ltEnd(Note const& a, Note const& b) { return a.end < b.end; }
  private:
	double scoreMultiplier() const;
};

typedef std::vector<Note> Notes;

class VocalTrack {
public:
	VocalTrack(std::string name);
	void reload();
	std::string name;
	Notes notes;
	int noteMin, noteMax; ///< lowest and highest note
	double beginTime, endTime; ///< the period where there are notes
	double m_scoreFactor; ///< normalization factor for the scoring system
	MusicalScale scale; ///< scale in which song is sung
};

typedef std::map<std::string, VocalTrack> VocalTracks;

struct DanceTrack {
	DanceTrack(std::string& description, Notes& notes);
	//track description
	std::string description;
	//container for the actual note data
	Notes notes;
};

enum DanceDifficulty {
	BEGINNER,
	EASY,
	MEDIUM,
	HARD,
	CHALLENGE,
	DIFFICULTYCOUNT
};

typedef std::map<DanceDifficulty, DanceTrack> DanceDifficultyMap;
typedef std::map<std::string, DanceDifficultyMap> DanceTracks;