📄 实时音频信号采集和处理系统.m
字号:
function demoai_fft(varargin)%%% Error if an output argument is supplied.if nargout > 0 error('Too many output arguments.');end%%% Based on the number of input arguments call the appropriate % local function.switch nargincase 0 % Create the analog input object. data = localInitAI; % Create the figure. data = localInitFig(data); hFig = data.handle.figure; case 1 error('The ADAPTORNAME, ID and CHANID must be specified.');case 2 % Initialize variables. data = []; action=varargin{1}; hFig=varargin{2}; try data=get(hFig,'UserData'); catch e %#ok<NASGU> % This may fail if only the ADAPTORNAME and ID were input. However, % if the ID was 0, this will work. end % DATA will be empty if CHANID was not specified or if ID = 0. if isempty(data) error('The CHANID must be specified.'); end % Based on the action, call the appropriate local function. switch action case 'close' localClose(data); case 'stop' data = localStop(data); endcase 3 % User specified the input - adaptor, id, chanNum. % Create the analog input object. data = localInitAI(varargin{:}); % Create the figure. data = localInitFig(data); hFig = data.handle.figure;end%%% Update the figure's UserData.if ~isempty(hFig) && ishghandle(hFig), set(hFig,'UserData',data);end%%% Update the analog input object's UserData.if isvalid(data.ai) set(data.ai, 'UserData', data);end%% *********************************************************************** % Create the object and get the first fft.function data = localInitAI(varargin)% Initialize variables.data = [];%%% Either no input arguments or all three - ADAPTORNAME, ID and CHANNELID.switch nargincase 0 adaptor = 'winsound';%设置硬件设备对应名称 id = 0;%应用声卡则无需设置硬件设备标识 chan = 1;%选择左声道case 3 adaptor = varargin{1}; id = varargin{2}; chan = varargin{3};otherwise error('daq:demoai_fft:invalidparam','The ADAPTORNAME, ID and CHANID must be specified.');end%%% Error if more than one channel was specified.if length(chan) > 1 error('daq:demoai_fft:onechanonly','Only a single channel can be created.');end%%% Channel 2 for sound card is not allowed.if strcmpi(adaptor, 'winsound') && chan == 2 warning('daq:demoai_fft:winsoundchan1','Channel 1 must be used for device Winsound.'); chan = 1;end%%% Object Configuration.% Create an analog input object with one channel.ai = analoginput(adaptor, id);%建立模拟输入对象aiaddchannel(ai, chan);%添加输入信号Chan到ai%%% Configure the analog input object.set(ai, 'SampleRate', 44100);%设置采样频率timePeriod = 0.1;%%% Configure the analog input object to trigger manually twice.set(ai, 'SamplesPerTrigger', timePeriod*ai.sampleRate);set(ai, 'TriggerRepeat', 1);set(ai, 'TriggerType', 'manual');%%% Initialize callback parameters. The TimerAction is initialized % after figure has been created.set(ai, 'TimerPeriod', timePeriod); set(ai, 'BufferingConfig',[2048,20]);%每次采集后分配的空间为2048,共存储20次%%% Object Execution.% Start the analog input object.start(ai);%开始采样trigger(ai);%启动触发%%% Obtain the available time and data.[d,time] = getdata(ai, ai.SamplesPerTrigger);%数据和时间的二维表,获得采样值向量%%% Calculate the fft.Fs = get(ai, 'SampleRate');%提取采样数据blockSize = get(ai, 'SamplesPerTrigger');%设置数据块大小(采样点数)[f,DAQfft,mag,phas] = localDaqfft(d,Fs,blockSize);%对输入信号进行FFT、幅值及相位运算[d_filter,DAQfft_filter,mag_filter,phas_filter] = localDaqfft_filter1(d,Fs,blockSize);%对输入信号先进行巴特沃斯滤波,然后进行FFT、幅值及相位运算%%% Update the data structure.data.ai = ai;data.getdata = [d time];data.daqfft =[f DAQfft];data.daqfftmag = [f mag];data.daqfftphas=[f phas];data.getdata_filter = [d_filter time];data.daqfft_filter =[f DAQfft_filter];data.daqfftmag_filter = [f mag_filter];data.daqfftphas_filter=[f phas_filter];data.handle = [];%%% Set the object's UserData to data.set(data.ai, 'UserData', data);%% *********************************************************************** % 创建显示框体。function data = localInitFig(data)%%% Initialize variables.btnColor=get(0,'DefaultUIControlBackgroundColor');%%% 将GUI放置在屏幕中央。screenUnits=get(0,'Units');set(0,'Units','pixels');screenSize=get(0,'ScreenSize');set(0,'Units',screenUnits);figWidth=600;figHeight=360; figPos=[(screenSize(3)-figWidth)/2 (screenSize(4)-figHeight)/2 ... figWidth figHeight];%%% 创建图形窗口。hFig=figure(... 'Color' ,btnColor ,... 'IntegerHandle' ,'off' ,... 'DoubleBuffer' ,'on' ,... 'DeleteFcn' ,'demoai_fft(''close'',gcbf)',... 'MenuBar' ,'none' ,... 'HandleVisibility' ,'on' ,... 'Name' ,'数据采集系统' ,... 'Tag' ,'Analog Input FFT demo' ,... 'NumberTitle' ,'off' ,... 'Units' ,'pixels' ,... 'Position' ,figPos ,... 'UserData' ,[] ,... 'Colormap' ,[] ,... 'Pointer' ,'arrow' ,... 'Visible' ,'off' ... );%%% 绘制滤波前信号波形。hAxes(1) = axes(...%调用设置好的hAxes(1)句柄,根据参数对图像的两个轴进行绘制(210,566行) 'Position' , [0.05 0.6 0.19 0.3],... 'Parent' , hFig,... 'XLim' , [0 get(data.ai, 'SamplesPerTrigger')],... 'YLim' , [-0.5 0.5]... );hLine(1) = plot(data.getdata(:,1));%调用设置好的hLine(1)句柄,利用Plot函数对采样的图像进行实时绘制set(hAxes(1), 'XLim', [0 get(data.ai, 'SamplesPerTrigger')]);%设置hAxes(1)句柄的属性,运用采样点数对X轴进行控制xlabel('采样点');ylabel('模拟输入 (V)');title('滤波前的信号波形');%%% 绘制滤波前信号频谱。hAxes(2) = axes(... 'Position' , [0.29 0.6 0.19 0.3],... 'Parent' , hFig,... 'XLim' , [0 max(data.daqfft(:,1))]... );hLine(2) = plot(data.daqfft(:,1),data.daqfft(:,2));set(hAxes(2), 'XLim', [0 5000]);xlabel('频率 (Hz)');ylabel('');title('滤波前信号频谱');%%% 绘制滤波前信号幅度谱。hAxes(3) = axes(... 'Position' , [0.54 0.6 0.19 0.3],... 'Parent' , hFig,... 'XLim' , [0 max(data.daqfftmag(:,1))]... );hLine(3) = plot(data.daqfftmag(:,1),data.daqfftmag(:,2));set(hAxes(3), 'XLim', [0 max(data.daqfftmag(:,1))]);xlabel('频率(Hz)');ylabel('幅值(dB)');title('滤波前信号对数幅频特性');%%% 绘制滤波前信号相位谱。hAxes(4) = axes(... 'Position' , [0.79 0.6 0.19 0.3],... 'Parent' , hFig,... 'XLim' , [0 max(data.daqfftphas(:,1))]... );hLine(4) = plot(data.daqfftphas(:,1),data.daqfftphas(:,2));set(hAxes(4), 'XLim', [0 max(data.daqfftphas(:,1))]);xlabel('频率 (Hz)');ylabel('相位角(角度)');title('滤波前信号相位谱');%%% 绘制滤波后信号波形。hAxes(5) = axes(... 'Position' , [0.05 0.15 0.19 0.3],... 'Parent' , hFig,... 'XLim' , [0 get(data.ai, 'SamplesPerTrigger')],... 'YLim' , [-0.5 0.5]... );hLine(5) = plot(data.getdata_filter(:,1));set(hAxes(5), 'XLim', [0 get(data.ai, 'SamplesPerTrigger')]);xlabel('采样点');ylabel('模拟输入 (V)');title('滤波后的信号波形');%%% 绘制滤波后信号频谱。hAxes(6) = axes(... 'Position' , [0.29 0.15 0.19 0.3],... 'Parent' , hFig,... 'XLim' , [0 max(data.daqfft_filter(:,1))]... );hLine(6) = plot(data.daqfft_filter(:,1),data.daqfft_filter(:,2));set(hAxes(6), 'XLim', [0 5000]);xlabel('频率 (Hz)');ylabel('');title('滤波后信号频谱');%%% 绘制滤波后信号幅度谱。hAxes(7) = axes(... 'Position' , [0.54 0.15 0.19 0.3],... 'Parent' , hFig,... 'XLim' , [0 max(data.daqfftmag_filter(:,1))]... );hLine(7) = plot(data.daqfftmag_filter(:,1),data.daqfftmag_filter(:,2));set(hAxes(7), 'XLim', [0 max(data.daqfftmag_filter(:,1))]);xlabel('频率(Hz)');ylabel('幅值(dB)');title('滤波后信号对数幅频特性');%%% 绘制滤波后信号相位谱。hAxes(8) = axes(... 'Position' , [0.79 0.15 0.19 0.3],... 'Parent' , hFig,... 'XLim' , [0 max(data.daqfftphas_filter(:,1))]... );hLine(8) = plot(data.daqfftphas_filter(:,1),data.daqfftphas_filter(:,2));set(hAxes(8), 'XLim', [0 max(data.daqfftphas_filter(:,1))]);xlabel('频率 (Hz)');ylabel('相位角(角度)');title('滤波后信号相位谱');%%% 创建一个开始/暂停按钮。htoggle = uicontrol(...
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -