-
Notifications
You must be signed in to change notification settings - Fork 0
/
helpers.c
100 lines (87 loc) · 2.04 KB
/
helpers.c
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
// Helper functions for music
#include <cs50.h>
#include <math.h>
#include <string.h>
#include <stdio.h>
#include "helpers.h"
const char *ALL_NOTES[] = {"C", "C#", "D", "D#", "E", "F",
"F#", "G", "G#", "A", "A#", "B"
};
const int numNotes = 12;
// Converts a fraction formatted as X/Y to eighths
int duration(string fraction)
{
int numerator = atoi(strtok(fraction, "/"));
int denominator = atoi(strtok(NULL, "/"));
int duration = numerator * 8 / denominator;
return duration;
}
// Determines whether a string represents a rest
bool is_rest(string s)
{
return (
!strcmp(s, "\r")
|| !strcmp(s, "\n")
|| !strcmp(s, "\r\n")
|| !strcmp(s, "")
);
}
int getOctave(char *note)
{
int size = strlen(note);
int octave = note[size - 1] - '0';
octave = octave - 4;
return octave;
}
int getPosition(char *note, int isFlat)
{
for (int i = 0; i < numNotes; ++i)
{
if (strcmp(ALL_NOTES[i], note) == 0)
{
if (isFlat)
{
return i - 10;
}
return i - 9;
}
}
return 0;
}
void getPitch(char *pitch, char *note, int *isFlat)
{
int size = strlen(note);
if (size == 3)
{
char second = note[1];
if (second == 'b')
{
*isFlat = 1;
memcpy(pitch, ¬e[0], 1);
pitch[1] = '\0';
}
else
{
memcpy(pitch, ¬e[0], 2);
pitch[2] = '\0';
}
}
else if (size == 2)
{
memcpy(pitch, ¬e[0], 1);
pitch[1] = '\0';
}
}
// Calculates frequency (in Hz) of a note
int frequency(string note)
{
char pitch[3];
int isFlat = 0;
getPitch(pitch, note, &isFlat);
int semitones = getPosition(pitch, isFlat);
int octave = getOctave(note);
semitones += octave * 12;
float hz = 440 * pow(2, ((float) semitones / 12));
int rounded = (int) round(hz);
return rounded;
}