Форум по Delphi программированию

Delphi Sources



Вернуться   Форум по Delphi программированию > Все о Delphi > Мультимедиа
Ник
Пароль
Регистрация <<         Правила форума         >> FAQ Пользователи Календарь Поиск Сообщения за сегодня Все разделы прочитаны

Ответ
 
Опции темы Поиск в этой теме Опции просмотра
  #46  
Старый 12.08.2012, 16:09
Аватар для poli-smen
poli-smen poli-smen вне форума
Профессионал
 
Регистрация: 06.08.2012
Адрес: Кривой Рог
Сообщения: 1,791
Версия Delphi: Delphi 7, XE2
Репутация: 4415
По умолчанию

Цитата:
Сообщение от Dmitry_DM
Странно, но я не могу найти как записать буфер в массив. Когда-то видел статью, но не помню по какому запросу. Не подскажите как сделать эту операцию?
А какой тип буфера и какой тип массива?
Ответить с цитированием
  #47  
Старый 12.08.2012, 16:15
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Цитата:
Сообщение от poli-smen
А какой тип буфера и какой тип массива?
Тип буфера тот, что используется в моей программе (я не нашел в коде его тип), а тип массива я же не знаю, вы порекомендовали
Код:
Sample := Massiv[I, J];

Но тип не сказали. Наверное Integer или Int64.

Последний раз редактировалось Dmitry_DM, 12.08.2012 в 16:19.
Ответить с цитированием
  #48  
Старый 12.08.2012, 16:18
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Цитата:
Сообщение от poli-smen
Ну и соответственно в процедуру WriteWav добавь параметр для имени файла, который будешь использовать при создании потока TFileStream.
То-есть сделать так:
Код:
procedure WriteWav(Sender: TObject);

или так:
Код:
procedure WriteWav(FileName, fmOpenReadWrite);

Последний раз редактировалось Dmitry_DM, 12.08.2012 в 16:30.
Ответить с цитированием
  #49  
Старый 12.08.2012, 16:51
Аватар для poli-smen
poli-smen poli-smen вне форума
Профессионал
 
Регистрация: 06.08.2012
Адрес: Кривой Рог
Сообщения: 1,791
Версия Delphi: Delphi 7, XE2
Репутация: 4415
По умолчанию

Цитата:
Сообщение от Dmitry_DM
То-есть сделать так:
Код:
procedure WriteWav(Sender: TObject);

или так:
Код:
procedure WriteWav(FileName, fmOpenReadWrite);
Так:
Код:
procedure WriteWav(const FileName: String);
Ответить с цитированием
  #50  
Старый 12.08.2012, 17:36
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Цитата:
Сообщение от poli-smen
А какой тип буфера и какой тип массива?
Так что там на счет буфера и массива можно сделать?
Ответить с цитированием
  #51  
Старый 12.08.2012, 18:06
Аватар для poli-smen
poli-smen poli-smen вне форума
Профессионал
 
Регистрация: 06.08.2012
Адрес: Кривой Рог
Сообщения: 1,791
Версия Delphi: Delphi 7, XE2
Репутация: 4415
По умолчанию

Цитата:
Сообщение от Dmitry_DM
Так что там на счет буфера и массива можно сделать?
Хм... Странно. Вроде писал ответ на этот вопрос. Или это мне приснилось?
Хотя наверно просто нажал кнопку "Предварительный просмотр сообщения" вместо "Ответить"...

Я тоже не нашёл в вашей программе типа буфера. Значит его нужно объявлять и заполнять. А ещё лучше использовать в качестве буфера тот-же массив. Тогда первая процедура (ReadWave) заполнит этот буфер-массив, а вторая (WriteWav) прочитает из этого массива и запишет в wav-файл.
Ответить с цитированием
  #52  
Старый 12.08.2012, 20:40
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Цитата:
Сообщение от poli-smen
Хм... Странно. Вроде писал ответ на этот вопрос. Или это мне приснилось?
Хотя наверно просто нажал кнопку "Предварительный просмотр сообщения" вместо "Ответить"...

Я тоже не нашёл в вашей программе типа буфера. Значит его нужно объявлять и заполнять. А ещё лучше использовать в качестве буфера тот-же массив. Тогда первая процедура (ReadWave) заполнит этот буфер-массив, а вторая (WriteWav) прочитает из этого массива и запишет в wav-файл.
Все так запутанно и туманно.. Можно както по подробнее и с фрагментами кода?
Ответить с цитированием
  #53  
Старый 12.08.2012, 20:57
Аватар для poli-smen
poli-smen poli-smen вне форума
Профессионал
 
Регистрация: 06.08.2012
Адрес: Кривой Рог
Сообщения: 1,791
Версия Delphi: Delphi 7, XE2
Репутация: 4415
По умолчанию

Цитата:
Сообщение от Dmitry_DM
Все так запутанно и туманно.. Можно както по подробнее и с фрагментами кода?
Да куда уж подробнее? Достаточно объявить самый обычный двумерный динамический массив.
Почему двумерный? Чтобы в одном измерении хранить сэмплы, а в другом каналы этих сэмплов.
Почему динамический? Потому что нам заранее неизвестно сколько будет сэмплов и сколько каналов в читаемом wav-файле.
Пример:
Код:
type
  TMassiv = array of array of Integer;
Всё просто. Вот помню когда начинал только программировать на Delphi, а начинал я с Delphi 3 (потому что более новых версий в то время просто ещё не существовало), так вот в нём небыло динамических массивов. Приходилось заморачиваться, чтобы работать с массивами, размер которых не был известен заранее. А если ещё нужен был двумерный динамический массив, то вообще труба - код становился совершенно трудночитаемый и трудноиспользуемый...
Ответить с цитированием
  #54  
Старый 12.08.2012, 22:46
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Цитата:
Сообщение от poli-smen
Да куда уж подробнее? Достаточно объявить самый обычный двумерный динамический массив.
Почему двумерный? Чтобы в одном измерении хранить сэмплы, а в другом каналы этих сэмплов.
Почему динамический? Потому что нам заранее неизвестно сколько будет сэмплов и сколько каналов в читаемом wav-файле.
Пример:
Код:
type
  TMassiv = array of array of Integer;
Всё просто. Вот помню когда начинал только программировать на Delphi, а начинал я с Delphi 3 (потому что более новых версий в то время просто ещё не существовало), так вот в нём небыло динамических массивов. Приходилось заморачиваться, чтобы работать с массивами, размер которых не был известен заранее. А если ещё нужен был двумерный динамический массив, то вообще труба - код становился совершенно трудночитаемый и трудноиспользуемый...
Ну вот! У меня что-то получилось! Вот только можете отредактировать программу, что бы работало это считывания массива, и связанное с ним (что бы бралась информация для записи из него).
Вложения
Тип файла: rar Read inf From WAV.rar (537.3 Кбайт, 11 просмотров)
Ответить с цитированием
  #55  
Старый 13.08.2012, 12:22
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Ну помогите хоть кто-нибудь! Я уже не знаю, как там еще пробовать, пол ночи просидел, только ошибки с этими массивами, а вручную, получается на один раз, если предварительно написать все в самой программе.
Ответить с цитированием
  #56  
Старый 14.08.2012, 12:16
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Здравствуйте еще раз! Вот процедура:
Код:
procedure WriteWav(const FileName: String);
type
  TMassiv = array of array of Integer;
  TChunkID = packed array [0..3] of Char;
  THeader = packed record
    ChunkID       : TChunkID;
    ChunkSize     : Longword;
    Format        : TChunkID;
    Subchunk1ID   : TChunkID;
    Subchunk1Size : Longword;
    AudioFormat   : Word;
    NumChannels   : Word;
    SampleRate    : Longword;
    ByteRate      : Longword;
    BlockAlign    : Word;
    BitsPerSample : Word;
    Subchunk2ID   : TChunkID;
    Subchunk2Size : Longword;
  end;
 
var
  Header: THeader;
  NumSamples, BytsPerSample, Sample, I, J: Longword;
  fs: TFileStream;
  Massiv: TMassiv;
begin
  NumSamples := 1079; {Massiv[I, J];}
  BytsPerSample := 2;

  Header.ChunkID       := 'RIFF'
  Header.Format        := 'WAVE';
  Header.Subchunk1ID   := 'fmt ';
  Header.Subchunk1Size := 16;
  Header.AudioFormat   := $0001;
  Header.NumChannels   := 1;
  Header.SampleRate    := 22050;
  Header.BitsPerSample := BytsPerSample * 8;
  Header.BlockAlign    := Header.NumChannels * BytsPerSample;
  Header.ByteRate      := Header.SampleRate * Header.BlockAlign;
  Header.Subchunk2ID   := 'data';
  Header.Subchunk2Size := NumSamples * Header.BlockAlign;
  Header.ChunkSize     := Header.Subchunk2Size + SizeOf(Header) - 8;

  fs := TFileStream.Create('New File.wav',fmCreate);
  try
    fs.WriteBuffer(Header, SizeOf(Header));

    for I := 1 to NumSamples do
    begin
      for J := 1 to Header.NumChannels do
      begin
        Sample := 1111;
        fs.WriteBuffer(Sample, BytsPerSample);
      end;
    end;
  finally
    fs.Free;
  end;
end;
procedure TForm1.Button4Click(Sender: TObject);
begin
  if SaveDialog2.Execute then
  begin
    WriteWav(SaveDialog2.FileName);
  end;
  end;
Для записи Wav требуются
Код:
Header.ChunkID       := 'RIFF'
  Header.Format        := 'WAVE';
  Header.Subchunk1ID   := 'fmt ';
  Header.Subchunk1Size := 16;
  Header.AudioFormat   := $0001;
  Header.NumChannels   := 1;
  Header.SampleRate    := 22050;
  Header.BitsPerSample := BytsPerSample * 8;
  Header.BlockAlign    := Header.NumChannels * BytsPerSample;
  Header.ByteRate      := Header.SampleRate * Header.BlockAlign;
  Header.Subchunk2ID   := 'data';
  Header.Subchunk2Size := NumSamples * Header.BlockAlign;
  Header.ChunkSize     := Header.Subchunk2Size + SizeOf(Header) - 8;
Собственно вопрос: как сделать, чтобы данные не вводить, а считывать строки из memo2 ? Перед этим в memo2 записывается содержимое txt файла.
Наверное надо сделать как то так:
Код:
Header.ChunkID       := ReadString.Memo2('RIFF');
Но как-то правильнее....
Ответить с цитированием
  #57  
Старый 14.08.2012, 13:07
Аватар для poli-smen
poli-smen poli-smen вне форума
Профессионал
 
Регистрация: 06.08.2012
Адрес: Кривой Рог
Сообщения: 1,791
Версия Delphi: Delphi 7, XE2
Репутация: 4415
По умолчанию

Цитата:
Сообщение от Dmitry_DM
Здравствуйте еще раз! Вот процедура:
Код:
procedure WriteWav(const FileName: String);
Сразу же вопрос. Зачем нужен параметр FileName если он в этой процедуре не используется?

Цитата:
Сообщение от Dmitry_DM
Для записи Wav требуются
Код:
Header.ChunkID       := 'RIFF'
  Header.Format        := 'WAVE';
  Header.Subchunk1ID   := 'fmt ';
  Header.Subchunk1Size := 16;
  Header.AudioFormat   := $0001;
  Header.NumChannels   := 1;
  Header.SampleRate    := 22050;
  Header.BitsPerSample := BytsPerSample * 8;
  Header.BlockAlign    := Header.NumChannels * BytsPerSample;
  Header.ByteRate      := Header.SampleRate * Header.BlockAlign;
  Header.Subchunk2ID   := 'data';
  Header.Subchunk2Size := NumSamples * Header.BlockAlign;
  Header.ChunkSize     := Header.Subchunk2Size + SizeOf(Header) - 8;
Собственно вопрос: как сделать, чтобы данные не вводить, а считывать строки из memo2 ? Перед этим в memo2 записывается содержимое txt файла.
Наверное надо сделать как то так:
Код:
Header.ChunkID       := ReadString.Memo2('RIFF');
Но как-то правильнее....
Нет. Надо делать так:
Код:
Header.ChunkID := Memo2.Lines[X];
Где X - номер строки в Memo2 из которой нужно прочитать данные.
Ответить с цитированием
  #58  
Старый 14.08.2012, 14:04
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Цитата:
Сообщение от poli-smen
Сразу же вопрос. Зачем нужен параметр FileName если он в этой процедуре не используется?


Нет. Надо делать так:
Код:
Header.ChunkID := Memo2.Lines[X];
Где X - номер строки в Memo2 из которой нужно прочитать данные.
Код:
Header.ChunkID := Memo2.Lines[X];

Так не получается... Вот такое выдает:
Вложения
Тип файла: rar Безымянный.rar (163.5 Кбайт, 4 просмотров)
Ответить с цитированием
  #59  
Старый 14.08.2012, 14:33
Аватар для poli-smen
poli-smen poli-smen вне форума
Профессионал
 
Регистрация: 06.08.2012
Адрес: Кривой Рог
Сообщения: 1,791
Версия Delphi: Delphi 7, XE2
Репутация: 4415
По умолчанию

Цитата:
Сообщение от Dmitry_DM
Код:
Header.ChunkID := Memo2.Lines[X];

Так не получается... Вот такое выдает:
Header.ChunkSize - имеет целочисленный тип, а в Memo хранятся только строки. Значит чтобы было возможно присвоение, нужно делать преобразование строки в число: StrToInt()
Ответить с цитированием
  #60  
Старый 14.08.2012, 14:48
Dmitry_DM Dmitry_DM вне форума
Активный
 
Регистрация: 07.08.2012
Сообщения: 258
Версия Delphi: Delphi 7
Репутация: 11
По умолчанию

Цитата:
Сообщение от poli-smen
Header.ChunkSize - имеет целочисленный тип, а в Memo хранятся только строки. Значит чтобы было возможно присвоение, нужно делать преобразование строки в число: StrToInt()
Так?
Код:
Header.ChunkSize     := StrToInt(Form1.Memo2.Lines[2]);
Корочее так правильно! Но теперь запись не происходит, пишет: 'wave' is not a valid integer value. Как теперь при записи сделать снова string?

Последний раз редактировалось Dmitry_DM, 14.08.2012 в 15:12.
Ответить с цитированием
Ответ


Delphi Sources

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск
Опции просмотра

Ваши права в разделе
Вы не можете создавать темы
Вы не можете отвечать на сообщения
Вы не можете прикреплять файлы
Вы не можете редактировать сообщения

BB-коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.
Быстрый переход


Часовой пояс GMT +3, время: 03:00.


 

Сайт

Форум

FAQ

RSS лента

Прочее

 

Copyright © Форум "Delphi Sources" by BrokenByte Software, 2004-2023

ВКонтакте   Facebook   Twitter