- •Предметная область разрабатываемой программы
- •2. Выбор средств разработки
- •3.1. Функциональное назначение программы
- •3.2 Требования к надежности
- •3.3. Общее описание программы
- •3.4. Описание логической структуры
- •3.5 Реализация программы
- •3.6 Выходные файлы
- •3.7 Тестирование программы
- •3.8 Описание экранных форм
- •Заключение.
3.1. Функциональное назначение программы
Программа «Основные компоненты нотного редактора» предназначена для создания, редактирования, прослушивания (воспроизведения), сохранения и загрузки созданных в ней мелодий. Количество октав – 2. Сохранение и загрузка мелодий осуществляется с помощью файлов расширения *.mus.
Программа должна быть предназначена для использования на персональных компьютерах стандартной комплектации.
3.2 Требования к надежности
Разрабатываемая система должна выдавать сообщения о возникающих ошибках при неверном задании исходных данных, поддерживать диалоговый режим в рамках предоставляемых пользователю возможностей.
Конечный пользователь не должен иметь свободный доступ к исходным файлам системы. Для модификации программой части системы пользователю необходимо обращаться к разработчику.
3.3. Общее описание программы
Разработанная программа имеет наименование «Основные компоненты нотного редактора». Программа написана на языке C++ в среде разработки C++ Builder 6.0. Исполняемый файл программы Music_Redactor.exe. В качестве звучания нот используются MIDI-файлы, которые были созданы и экспортированы в звуковом редакторе Guitar Pro 5.1. Каждая нота это один MIDI-файл. Основное различие музыки, записанной в виде MIDI-сообщений и в виде нот на бумаге, заключается в том,
что MIDI-запись – это зафиксированный объект, где каждая нота имеет точное значение по громкости и длительности.Темп этой записи в каждый момент имеет тоже точное фиксированное значение.
Входными данными программы должны быть скорость воспроизведения и файлы расширения *.mus, созданные программой ранее либо набранная пользователем мелодия. Выходными данными являются набранная мелодия, которую можно сохранить в виде файла расширения *.mus. Используются четыре вида длительностей ноты: восьмая, четвёртая, половинная и целая.
3.4. Описание логической структуры
Проект включает в себя 3 модуля и 3 формы соответственно.
Форма F1 (модуль MainUnit) – главная форма проекта, отвечает за отображение октав и нотного стана, ввод мелодии, её загрузку, сохранение и воспроизведение. На форме располагается меню программы, посредством которого запускаются все остальные формы.
Форма F2 (модуль DlitUnit) – форма задания длительностей звучания нот.
Форма FSpravka (модуль Spravka) – форма со справочной информацией о программе.
В разработке программы использовались следующие компоненты среды:
TBitBtn – кнопка с картинкой,
TMemo – многострочное окно ввода,
TMainMenu – меню,
ApplicationEvents – компонент позволяет реагировать на действия пользователя, в частности на нажатия кнопки клавиатуры.
TMediaplayer – компонент для воспроизведения MIDI-файлов.
TRadioButton – компонент используются для выбора пользователем длительности ноты.
3.5 Реализация программы
Набор нот в программе может производится как с помощью клавиатуры, так и с помощью виртуального фортепиано, расположенного на главной форме F1.
Набор нот на фортепиано осуществляется с помощью метода:
void __fastcall TF1::BitBtn1Click(TObject *Sender) //нота ДО
{
switch(Dlit_noti)
{
case 1:nota=notes_cat+"\\doV.mid";break;
case 2:nota=notes_cat+"\\do.mid";break;
case 3:nota=notes_cat+"\\doP.mid";break;
case 4:nota=notes_cat+"\\do16.mid";break;
}
D=D+IntToStr(Dlit_noti);
get_nota(¬a);
t=Memo1->SelStart;
s=Memo1->Text;
s.Insert("d",Memo1->SelStart+1);
Memo1->Text=s;
Memo1->SelStart=t+1;
F1->Memo1->SetFocus();
}
Набор той же ноты с помощью клавиатуры:
void __fastcall TF1::ApplicationEvents1Message(tagMSG &Msg,
bool &Handled)
{
switch(Msg.wParam)
{
….
case 81:
a=1;
BitBtn1->SetFocus();
BitBtn1->Click();
Break;
…
}
В программе имеется две октавы. Первой октаве соответствуют клавиши на клавиатуре:
“Q”,”W”,”E”,”R”,”T”,”Y”,”U”.
В нотном стане они отображаются как:
“d, r, m, f, s, l ,c”
Второй октаве соответствуют клавиши на клавиатуре:
“A”,”S”,”D”,”F”,”G”,”H”,”J”. В нотном стане отображаются как:
“D, R, M, F, S, L ,C”.
Диезам и бемолям соответствуют клавиши: 1,2,3,4,5,6,7,8,9,10
Воспроизведение ноты осуществляет функция get-nota.В качестве параметра функция принимает название ноты(midi-файла) и с помощью компонента TMediaplayer воспроизводит её:
void get_nota(AnsiString *nota)
{
F1->MediaPlayer1->FileName=*nota;
F1->MediaPlayer1->Open();
F1->MediaPlayer1->Play();
}
Воспроизведение мелодии осуществляется с помощью компонента TTimer. После того как мелодия набрана или загружена и нажата клавиша воспроизведения, наступает событие OnTimer. Интервал таймера настраивается под длительность каждой ноты, чтобы каждая нота «успела» воспроизвестись или же наоборот не было избытка времени при воспроизведении ноты:
void __fastcall TF1::Timer1Timer(TObject *Sender)
{
i=i+1;
if(i==z.Length()){Timer1->Enabled=false;}
if(D[i]=='1')Timer1->Interval=400;
if(D[i]=='2')Timer1->Interval=800;
if(D[i]=='3')Timer1->Interval=1000;
if(D[i]=='4')Timer1->Interval=300;
if (z[i]=='d')
{
BitBtn1->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\doV.mid";break;
case 2: nota=notes_cat+"\\do.mid";break;
case 3:nota=notes_cat+"\\doP.mid";break;
case 4:nota=notes_cat+"\\do16.mid";break;
}
get_nota(¬a);
}
else
if(z[i]=='r')
{
BitBtn2->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\reV.mid";break;
case 2: nota=notes_cat+"\\re.mid";break;
case 3:nota=notes_cat+"\\reP.mid";break;
case 4:nota=notes_cat+"\\re16.mid";break;
}
get_nota(¬a);
}
if (z[i]=='m')
{
BitBtn3->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\miV.mid";break;
case 2: nota=notes_cat+"\\mi.mid";break;
case 3:nota=notes_cat+"\\miP.mid";break;
case 4:nota=notes_cat+"\\mi16.mid";break;
}
get_nota(¬a);
}
if (z[i]=='f')
{
BitBtn4->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\faV.mid";break;
case 2: nota=notes_cat+"\\fa.mid";break;
case 3:nota=notes_cat+"\\faP.mid";break;
case 4:nota=notes_cat+"\\fa16.mid";break;
}
get_nota(¬a);
}
if (z[i]=='s')
{
BitBtn5->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\soV.mid";break;
case 2: nota=notes_cat+"\\so.mid";break;
case 3:nota=notes_cat+"\\soP.mid";break;
case 4:nota=notes_cat+"\\so16.mid";break;
}
get_nota(¬a);
}
if (z[i]=='l')
{
BitBtn6->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\laV.mid";break;
case 2: nota=notes_cat+"\\la.mid";break;
case 3:nota=notes_cat+"\\laP.mid";break;
case 4:nota=notes_cat+"\\la16.mid";break;
}
get_nota(¬a);
}
if (z[i]=='c')
{
BitBtn7->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\siV.mid";break;
case 2: nota=notes_cat+"\\si.mid";break;
case 3:nota=notes_cat+"\\siP.mid";break;
case 4:nota=notes_cat+"\\si16.mid";break;
}
get_nota(¬a);
}
if (z[i]=='D')
{
BitBtn8->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\doV2.mid";break;
case 2: nota=notes_cat+"\\do2.mid";break;
case 3:nota=notes_cat+"\\doP2.mid";break;
case 4:nota=notes_cat+"\\do16_2.mid";break;
}
get_nota(¬a);
}
if (z[i]=='R')
{
BitBtn9->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\reV2.mid";break;
case 2: nota=notes_cat+"\\re2.mid";break;
case 3:nota=notes_cat+"\\reP2.mid";break;
case 4:nota=notes_cat+"\\re16_2.mid";break;
}
get_nota(¬a);
}
if (z[i]=='M')
{
BitBtn10->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\miV2.mid";break;
case 2: nota=notes_cat+"\\mi2.mid";break;
case 3:nota=notes_cat+"\\miP2.mid";break;
case 4:nota=notes_cat+"\\mi16_2.mid";break;
}
get_nota(¬a);
}
if (z[i]=='1')
{
BitBtn15->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\doV_diez.mid";break;
case 2: nota=notes_cat+"\\do_diez.mid";break;
case 3:nota=notes_cat+"\\doP_diez.mid";break;
case 4:nota=notes_cat+"\\do16_diez.mid";break;
}
get_nota(¬a);
}
if (z[i]=='2')
{
BitBtn16->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\reV_diez.mid";break;
case 2: nota=notes_cat+"\\re_diez.mid";break;
case 3:nota=notes_cat+"\\reP_diez.mid";break;
case 4:nota=notes_cat+"\\re16_diez.mid";break;
}
get_nota(¬a);
}
if (z[i]=='3')
{
BitBtn17->SetFocus();
Memo1->Text=Memo1->Text+z[i];
Memo1->Update();
switch(StrToInt(D[i]))
{
case 1:nota=notes_cat+"\\faV_diez.mid";break;
case 2: nota=notes_cat+"\\fa_diez.mid";break;
case 3:nota=notes_cat+"\\faP_diez.mid";break;
case 4:nota=notes_cat+"\\fa16_diez.mid";break;
}
get_nota(¬a);
if(!Timer1->Enabled)i=0;
}
Глобальная переменная Dlit_noti хранит значение длительности ноты: 1,2,3 или 4.