cyfile / Matlab-base-toolbox

本人使用Matlab基础工具箱所编写的各种代码
1 stars 0 forks source link

m3u8文件解析 + 音频截取 #23

Open 213cy opened 3 years ago

213cy commented 3 years ago

由三个文件构成 了一个解析下载提取douyu视频中的部分语音的程序 其中还用到了 Statistics and Machine Learning Toolbox 里的函数: quantile

213cy commented 3 years ago

主程序:

url = clipboard('paste');
temp = regexp(url,'playlist.m3u8','split');
pref = temp{1};

websave('playlist.m3u8',url);
fileID = fopen('playlist.m3u8','r');
dataArray = textscan(fileID, '%s%*s',10,'Whitespace',':', 'TextType', 'string');
for k=1:10
    if dataArray{1}(k) == "#EXTINF"
        break
    end
end
suf = dataArray{1}(k+1);

frewind(fileID);
dataArray = textscan(fileID, '%*s%f%*s','Delimiter',{',',':'},...
    'Whitespace','\n\r', 'EndOfLine', '#' ,'HeaderLines', k);
fclose(fileID);
%ftell(fileID)
tcum= cumsum( dataArray{1} );

clear url dataArray fileID k

%%
temp = 10311;
vind = find(tcum<60*floor(temp/100)+mod(temp,100),1,'last');
% if isempty(ind) ind = 0
% vind = vind +1;
%%
filename = [num2str(vind,'%03u') ,'.ts'];
newsuf = replace(suf,'000.ts',filename);
websave(filename, pref + newsuf);

[ans,~]=system( ['ffmpeg -i ',filename,' -vn -acodec copy a.mp4 -y'])
%!ffmpeg -i 999.ts -vn -acodec copy a.mp4 -y
[y,Fs] = audioread('a.mp4');
%%
%[ye,Fs] = audioread('HeroArchMageYes1.wav');
%[ye,Fs] = audioread('JainaPissed4.wav');
%plot(sort(abs(ye)));
%sound(ye,Fs);
%%
axes('Position',[0.04 0.15 0.95 0.8]);
plot(y(:,1))
%plot([y(:,1),y(:,2)+0.6])

a = [1,length(y)/2,length(y)];
uicontrol('Style', 'pushbutton', 'String', 'playAB',...
        'Position', [100 20 50 20],...
        'Callback', 'evalin(''base'', ''soundsc(y(min(a):median(a),1),Fs)'')');     
uicontrol('Style', 'pushbutton', 'String', 'playAC',...
        'Position', [250 20 50 20],...
        'Callback', 'evalin(''base'', ''soundsc(y(min(a):max(a),1),Fs)'')'); 
    uicontrol('Style', 'pushbutton', 'String', 'playBC',...
        'Position', [400 20 50 20],...
        'Callback', 'evalin(''base'', ''soundsc(y(median(a):max(a),1),Fs)'')');
hdt = datacursormode;
hdt.UpdateFcn = @(obj,event_obj) textupdate(obj,event_obj);

%%
yn=y(min(a):2:max(a),1);% downsample(y,2)
A =0.30/quantile(abs(yn),0.90);
yout = A*yn; 
audiowrite('out.wav',yout,Fs/2)
sound(yout,Fs/2);
%soundsc();
213cy commented 3 years ago

辅助截取音频片段的 pointdatatip 更新辅助函数

function output_txt = textupdate(obj,event_obj)
% Display the position of the data cursor
% obj          Currently not used (empty)
% event_obj    Handle to event object
% output_txt   Data cursor text string (string or cell array of strings).

persistent s
if isempty(s)|| ~isvalid(s.h(1))
    s.autoflag = false;
    s.d =[0 ,0,0];
    ylim = getfield(gca,'YLim');
    s.h =[line([0,0],ylim,'Color','m'),...
        line([0,0],ylim,'Color','c'),...
        line([0,0],ylim,'Color','y')];
    s.p =[0,0,0];
end

pos = get(event_obj,'Position');
n = pos(1);
v = pos(2);

if s.autoflag
    output_txt = ['X::',num2str(n)];
    s.autoflag = false;
    return
end

switch obj
    case s.p(1)
        pt = 1;
    case s.p(2)
        pt = 2;
    case s.p(3)
        pt = 3;
    otherwise
        switch 0
            case s.p(1)
                pt = 1;
                s.p(1)= obj;
            case s.p(2)
                pt = 2;
                s.p(2)= obj;
            case s.p(3)
                pt = 3;
                s.p(3)= obj;
            otherwise
                delete(obj)
                return
        end
end

%if ~s.autoflag
st = max(1,n-200);
en = min(n+200,numel(obj.DataSource.YData));

[~,ind] = min(abs( ...
    obj.DataSource.YData(st:en).*...
    [0.05*(n-st)+0.95:-0.05:1,1,1:0.05:0.05*(en-n)+0.95] ));
nn = st+ind-1;
vv = obj.DataSource.YData(nn);

s.h(pt).XData=[nn,nn];
s.d(pt) = nn;
assignin('base', 'a', s.d);
display([num2str(v),'==>',num2str(vv),'       ',num2str(n),'==>',num2str(nn)])

if nn == n
    output_txt = ['X==',num2str(n)];
else
    s.autoflag = true;
    obj.Position=[nn,vv,0];
end
%end
213cy commented 3 years ago

附加的降噪程序
同https://github.com/cyfile/Matlab-miscellanies/issues/16#issuecomment-802668744

x=y(min(a):median(a),1);
xn = y([median(a):max(a)],1);
Fs=44100;

%% STFT parameters
Nfft=1024;
Nwin=768; 
overlap=512; 
win = sqrt(hanning(Nwin,"periodic"));

%%  Estimate SNR
[~,~,~,Pn]= spectrogram(xn,win,overlap,Nfft); 
[Sx,~,~,Px] = spectrogram(x,win,overlap,Nfft); 
%%
% A=quantile(Pn,0.35,2).*quantile(Pn,0.65,2)./quantile(Pn,0.2,2)./quantile(Pn,0.8,2);
% noise_A= A.*quantile(Pn,0.5,2);
 noise_B= 2*quantile(Pn,0.35,2);
% noise_C= mean(Pn,2);
%noise_D= median(Pn,2);

noise_r= min( noise_B./Px  , 1 );

fa = db2mag(-3*[20:-1:0,1:20]);
fa = fa/sum(fa);
fb= db2mag(-12*[5:-1:0,1:5]);
fb = fb/sum(fb);
%noise_r = conv2(fb,fa,noise_r,'same');
noise_r = conv2(noise_r,fa,'same');
%noise_r = conv2(noise_r,fb','same');

beta1=0.5;
beta2=0.4;
lambda=logspace(log10(1.1),log10(4.5),Nfft/2+1)'; 
mask=max( 1-lambda.*noise_r.^beta1 , 0).^beta2;
%mask(Nwin/2-30:end,:)=0;
STFT=mask.*Sx;

%%  Compute inverse STFT and overlapp add
[Ft,Nt] = size(STFT);
Xtemp = ifft([STFT;conj(STFT(Ft-1:-1:2,:))] );
Xs = Xtemp(1:Nwin,:).*win;

hop = Nwin - overlap;
out=zeros((Nt-1)*hop + Nwin,1);
for index=1:Nt 
    ind=(index-1)*hop ;
    out(ind+1:ind+Nwin)= out(ind+1:ind+Nwin)+Xs(:,index);
end

display(['new out ' num2str(randi(999))])
return

%% -----------------    Listen results   ------------------------------------
%%
soundsc(xn,Fs);
soundsc(x,Fs);
soundsc(out,Fs);
figure,plot(out)
y=out;
%% -----------------    Display Figure   ------------------------------------      
%% show spectrogram
figure
subplot(211)
spectrogram(x,win,overlap,Nfft,Fs); 
colorbar(gca,'off')
subplot(212)
spectrogram(out,win,overlap,Nfft,Fs);
colorbar(gca,'off')