-
Notifications
You must be signed in to change notification settings - Fork 1
/
morse_Audio.cpp
132 lines (110 loc) · 3.79 KB
/
morse_Audio.cpp
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
124
125
126
127
128
129
130
131
132
#include <cmath>
#include <fstream>
#include <iostream>
#include <string>
using namespace std;
namespace little_endian_io{
template <typename Word>
std::ostream& write_word(std::ostream& outs, Word value, unsigned size = sizeof(Word))
{
for (; size; --size, value >>= 8)
outs.put(static_cast <char> (value & 0xFF));
return outs;
}
}
using namespace little_endian_io;
int main(int argc, const char* argv[])
{
string infilename;
string outfilename;
if(argc > 1)
infilename = argv[1];
else
infilename = "code.txt";
if(argc > 2)
outfilename = argv[2];
else
outfilename = "example.wav";
ofstream f(outfilename, ios::out|ios::binary);
// Write the file headers
f << "RIFF----WAVEfmt "; // (chunk size to be filled in later)
write_word(f, 16, 4); // no extension data
write_word(f, 1, 2); // PCM - integer samples
write_word(f, 2, 2); // two channels (stereo file)
write_word(f, 44100, 4); // samples per second (Hz)
write_word(f, 176400, 4); // (Sample Rate * BitsPerSample * Channels) / 8
write_word(f, 4, 2); // data block size (size of two integer samples, one for each channel, in bytes)
write_word(f, 16, 2); // number of bits per sample (use a multiple of 8)
// Write the data chunk header
long int data_chunk_pos = f.tellp();
f << "data----"; // (chunk size to be filled in later)
// Write the audio samples
// (We'll generate a single C4 note with a sine wave, fading from left to right)
constexpr double two_pi = 6.283185307179586476925286766559;
constexpr double max_amplitude = 32760; // "volume"
double hz = 44100; // samples per second
double frequency = 1000; // middle C
fstream code;
string scode;
code.open(infilename, ios::in);
//check if file opens successfully
if(!code)
return -1;
getline(code,scode);
code.close();
for (int j = 0; j < scode.size(); j++) {
if (scode[j] == '-') {
double seconds = 0.3; // time
int N = hz * seconds; // total number of samples
for (int n = 0; n < N; n++)
{
double amplitude = (double)n / N * max_amplitude;
double value = sin((two_pi * n * frequency) / hz);
write_word(f, (int)(amplitude * value), 2);
write_word(f, (int)((max_amplitude - amplitude) * value), 2);
}
}
else if(scode[j] == '.') {
cout << "YES";
double seconds = 0.1 ; // time
int N = hz * seconds; // total number of samples
for (int n = 0; n < N; n++)
{
double amplitude = (double)n / N * max_amplitude;
double value = sin((two_pi * n * frequency) / hz);
write_word(f, (int)(amplitude * value), 2);
write_word(f, (int)((max_amplitude - amplitude) * value), 2);
}
}
else{
double seconds = 0.3; // time
int N = hz * seconds; // total number of samples
for (int n = 0; n < N; n++)
{
double amplitude = (double)n / N * max_amplitude;
double value = 0;
write_word(f, (int)(amplitude * value), 2);
write_word(f, (int)((max_amplitude - amplitude) * value), 2);
}
}
double seconds = 0.1; // time
int N = hz * seconds; // total number of samples
for (int n = 0; n < N; n++)
{
double amplitude = (double)n / N * max_amplitude;
double value = 0;
write_word(f, (int)(amplitude * value), 2);
write_word(f, (int)((max_amplitude - amplitude) * value), 2);
}
cout << scode[j];
}
// (We'll need the final file size to fix the chunk sizes above)
size_t file_length = f.tellp();
// Fix the data chunk header to contain the data size
f.seekp(data_chunk_pos + 4);
write_word(f, file_length - data_chunk_pos + 8);
// Fix the file header to contain the proper RIFF chunk size, which is (file size - 8) bytes
f.seekp(0 + 4);
write_word(f, file_length - 8, 4);
return 0;
}