forum.boolean.name

forum.boolean.name (http://forum.boolean.name/index.php)
-   С# (http://forum.boolean.name/forumdisplay.php?f=128)
-   -   Bass.dll перехват потока (http://forum.boolean.name/showthread.php?t=18833)

RegIon 06.01.2014 00:27

Bass.dll перехват потока
 
Кароче, решил сделать вот:



что бы потолок под музыку "плясал".
Это дело управляется микроконтроллером, а данные о музычке передаются с компа.
1-Как мне спомощью bass.dll сделать спектрограмму выходного потока аудиокарты?
2-как в gtk#2 сделать что-то типо таймера, как в формах?

Нарыл исходник онного на Делфи

PHP код:

unit Unit1;

interface

uses
  Windows
, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  
Dialogs, StdCtrls, bass, ExtCtrls, mmsystem;

type
  TForm1 
= class(TForm)
    
ComboBox1: TComboBox;
    
Label1: TLabel;
    
Timer1: TTimer;
    
PaintBox1: TPaintBox;
    
procedure FormCreate(Sender: TObject);
    
procedure ComboBox1Change(Sender: TObject);
    
procedure Timer1Timer(Sender: TObject);
  private
    { Private 
declarations }
  public
    { Public 
declarations }
  
end;

var
  
Form1: TForm1;
  
chan: cardinal;

implementation

{$R *.dfm}

function 
RecordingCallback(Handle: HRECORD; buffer: Pointer; length, user: DWord): boolean; stdcall;
begin
  Result 
:= True
end
;

procedure TForm1.FormCreate(Sender: TObject);
var
  
a: Integer;
  
dName: PChar;
  
r_Init: boolean;
  
AVolume: Single;
begin
 MCISendString
(PChar('play ' + '1.mp3'),nil,0,0);


  if (
HIWORD(BASS_GetVersion) <> BASSVERSION) then begin
    MessageBox
(0, 'An incorrect version of BASS.DLL was loaded', nil, MB_ICONERROR);
    
Halt;
  
end;

  if 
not BASS_Init(-1, 44100, BASS_DEVICE_LATENCY, handle, nil) then begin
    MessageBox
(0,'Can''t initialize device',nil,MB_ICONERROR);
    Exit;
  
end;

  
r_init := BASS_RecordInit(0);
  
chan := BASS_RecordStart(44100, 2, MakeLong(0, 10), @RecordingCallback, nil); // Recording Channel
  
if (not R_Init) or (chan = 0) then begin
    Bass_Free
();
    
MessageBox(0,'Can''t initialize recording device',nil,MB_ICONERROR);
    
Halt;
  
end;

  
a := 0;
  
dName := BASS_RecordGetInputName(a);
  while 
dName <> nil do begin
    ComboBox1
.Items.Add(StrPas(dName));
    
// is this one currently "on"?
    
if (BASS_RecordGetInput(a, AVolume) and BASS_INPUT_OFF) = 0 then ComboBox1.ItemIndex := a;
    
Inc(a);
    
dName := BASS_RecordGetInputName(a);
  
end;
  
ComboBox1Change(Self); //update

  
BASS_RecordGetInput(ComboBox1.ItemIndex, AVolume);
  
BASS_ChannelPlay(chan, False);

  
Timer1.Enabled:=true;
end;

procedure TForm1.ComboBox1Change(Sender: TObject);
var
  
i: Integer;
  
r: Boolean;
  
AVolume: Single;
begin
  r 
:= True;
  
i := 0;
  while 
r do begin
    r 
:= BASS_RecordSetInput(i, BASS_INPUT_OFF, -1);
    
Inc(i);
  
end;
  
BASS_RecordSetInput(ComboBox1.ItemIndex, BASS_INPUT_ON, -1);
  
BASS_RecordGetInput(ComboBox1.ItemIndex, AVolume);
end;

procedure TForm1.Timer1Timer(Sender: TObject);
type  fftdata = array[1..256] of single;
var 
data : fftdata;
    
i, n : integer;
    
level: cardinal;
    
levelL, levelR: byte;
begin
 level 
:= BASS_ChannelGetLevel(chan);
 
levelL := loword(level)*100 div (maxword div 2);   // уровень в %
 
levelR := hiword(level)*100 div (maxword div 2);

 
Bass_ChannelGetData(chan, @data, BASS_DATA_FFT512);

 
With PaintBox1 do
 
begin
   Canvas
.FillRect(rect(0, 0, paintbox1.width, paintbox1.height));
   
Canvas.Pen.Color := clRED;
   for 
i := 1 to 256 do begin
     n 
:= 3*round(data[i] * 100);
     
PaintBox1.Canvas.MoveTo(i, 100);
     
PaintBox1.Canvas.LineTo(i, 100 - n);
   
end;
   
//Canvas.Rectangle(258,100,266,100-levelL);
   //Canvas.Rectangle(268,100,276,100-levelR);
 
end;
end;

end. 


и по нему написал:

Xamarin Studio
PHP код:

using System;
using Gtk;
using Un4seen.Bass;

public 
partial class MainWindow: Gtk.Window
{
    private 
int[] FFP;
    
int chan;
    private 
RECORDPROC _myRecProc;

    private 
bool MyRecording(int handle, IntPtr buffer, int length, IntPtr user)
    {
        return 
true;
    }

    public 
MainWindow () : base (Gtk.WindowType.Toplevel)
    {
        
Build ();

        
LoadList ();
        
GLib.Timeout.Add (100, new GLib.TimeoutHandler (Update));
    }


    public 
bool Update(){
        
int level = Bass.BASS_ChannelGetLevel(chan);
        
progressbar3.Fraction = ((float)Utils.LowWord32(level))/327680; // the left level 
        
progressbar4.Fraction  = ((float)Utils.HighWord32(level))/327680; // the right level

        
return true;
    }

    protected 
void LoadList(){


        
Bass.BASS_Init (-1, 44100, BASSInit.BASS_DEVICE_DEFAULT, this.Handle);

        
_myRecProc = new RECORDPROC(MyRecording);

        
chan = Bass.BASS_RecordStart (44100, 2, BASSFlag.BASS_RECORD_PAUSE, _myRecProc, IntPtr.Zero);
        
Bass.BASS_ChannelPlay (chan, false);

        
Bass.BASS_RecordInit(0); // init the default device 
        
string name;
        
int n = 0;
        for (
n=0; (name = Bass.BASS_RecordGetInputName(n)) != null; n++)
        {
            
combobox1.InsertText(n,name);
        }
        if (
n == 0)
            
combobox1.AppendText ("Нету(");
        else{
            
float vol = 0f;
            
int setting = Bass.BASS_RecordGetInput(0, ref vol);
            
//progressbar2.Fraction = vol;
        
}
    }
    protected 
void OnDeleteEvent (object sender, DeleteEventArgs a)
    {
        
Application.Quit ();
        
a.RetVal = true;
    }

    protected 
void OnFocus (object o, SetFocusArgs args)
    {

    }

    protected 
void OnChange (object sender, EventArgs e)
    {
        
TreeIter inter;
        
combobox1.GetActiveIter (out inter);
        
Bass.BASS_RecordSetInput (0,BASSInput.BASS_INPUT_ON,-1.0f); // хз как в gtk их выбирать
        
Bass.BASS_RecordGetInput (0);
        
Update ();
    }
} 



Ток прогрессбар как стоял, так и стоит

pax 06.01.2014 10:09

Ответ: Bass.dll перехват потока
 
Это очень специализированный вопрос, боюсь на него никто не ответит тут...

RegIon 06.01.2014 13:31

Ответ: Bass.dll перехват потока
 
Научился я получать каналы, но только микрофона=(, надо как-то походу читерить.

Неожиданность:

Первая запущенна напрямую с Xamarin'a, а вторая копия из бинарника, чую они на разных виртуальных машинах?Да?
Первая на Моно, а вторая на .net походу стартанула.

проект: http://rghost.ru/51435851
(думаю бинарник знаете где)

Понял в чем трабла.
В отсутствии стерио микшера у дров карты, создал VAC - заработало с картой=)


Часовой пояс GMT +4, время: 23:05.

vBulletin® Version 3.6.5.
Copyright ©2000 - 2026, Jelsoft Enterprises Ltd.
Перевод: zCarot