怎么把一张小尺寸图片贴进大尺寸图片里面呢
怎么把一个长和宽小的视频贴进长和宽大点的视频之中呢
下面有两种方法,直接融合和泊松融合
图像直接融合
%%图像直接融合
clear
clc
%%读取图像文件
I=double(imread('1.jpg'));
img=double(imread('4.jpg'));
figure(1),imshow(uint8(I));
% 直接拼接-------------------
[row,col,~]=size(img);
%法1 鼠标选择位置
% [y_start,x_start]=ginput(1);%获得1个鼠标点击位置
%法2 输入位置数据
x_start=100;y_start=10; %输入坐标(10,100)输入顺序Y,X
x_end=x_start+row-1;
y_end=y_start+col-1;
I(x_start:x_end,y_start:y_end, :)=img(:,:,:);
figure(2);imshow(uint8(I));title('直接拼接图');
视频帧直接融合
%视频直接融合
clc
clear
close all;
% addpath(fullfile(pwd, 'picture_ronghe'));
%读取原视频文件
[fastaFile,dirName]=uigetfile({'*.avi;*.mp4;*.rmvb;*.wmv','Video File(*.avi;*.mp4;*.rmvb;*.wmv)';...
'*.*', 'All Files (*.*)'}, ...
'Choose a Video File');
[~, name] = fileparts([dirName,fastaFile]);
vid = VideoReader([dirName,fastaFile]);
vid_numFrames = vid.NumFrames;
vid_Frame = read(vid, 1);imshow(vid_Frame),title('第一帧')
%读取放大后的视频
[fastaFile,dirName]=uigetfile({'*.avi;*.mp4;*.rmvb;*.wmv','Video File(*.avi;*.mp4;*.rmvb;*.wmv)';...
'*.*', 'All Files (*.*)'}, ...
'Choose a Video File');
[~, name2] = fileparts([dirName,fastaFile]);
vidAmp = VideoReader([dirName,fastaFile]);
vidAmp_numFrames = vidAmp.NumFrames;
outName = fullfile(dirName,[name '_ronghe.avi']);
vidOut = VideoWriter(outName);
vidOut.FrameRate = vid.FrameRate;
open(vidOut)
tic
% for i = 1 : min(vid.NumFrames,vidAmp.NumFrames)
for i = 1 :10
Frame = read(vid, i);%原视频帧
FrameAmp = read(vidAmp, i);%放大视频帧
I=Frame;img=FrameAmp;
%法1: 由鼠标选择融合位置
[y_start,x_start]=ginput(1);%获得1个鼠标点击的位置
%法2:直接输入融合位置坐标
%输入小视频左上角坐标位置,先输入Y,再输入X。 x_start=Y,y_start=X
% x_start=217; y_start=418;
[row_img,col_img,~]=size(img);
x_end=x_start+row_img-1;
y_end=y_start+col_img-1;
I(x_start:x_end,y_start:y_end, :)=img(:,:,:);
writeVideo(vidOut,im2uint8(I));
end
close(vidOut);
toc
fprintf('视频融合完成\n');
图像泊松融合 函数 create_AB.m
%%图像泊松融合
function [A,B]=create_AB(image_A,mask_A,image_B,mask_B)
%假设插入的图片为方形
%image_A为插入图片
%mask_A为背景图片的模子,待插入部分为0,不插入部分为1
global number
[hxb,lxb,~]=find(mask_B==0);
B=zeros(length(hxb),1);%创建B
s=[hxb';lxb'];
[s1,id1]=sort(s(1,:));
s_z=[s1;s(2,id1)];%将行下标和列下标的顺序整理为行优先
hxb=s_z(1,:);
lxb=s_z(2,:);
min_x=min(hxb);
min_y=min(lxb);
max_x=max(hxb);
max_y=max(lxb);
k=2;
for i=1:length(hxb)
mask_B(hxb(i),lxb(i))=k;
k=k+1;
end
if number==1
A=sparse(zeros(length(hxb),length(hxb)));
end
if number~=1
A=0;
end
k=1;%k为正在填写A矩阵的第k行
for i=min_x:max_x
for j=min_y:max_y
if i==min_x||i==max_x||j==min_y||j==max_y
if number==1%如果第一次运行该求A函数
A(k,k)=1;
end
B(k)=image_B(i,j);%边界点B为其像素值
k=k+1;
end
if i~=min_x && i~=max_x&&j~=min_y&&j~=max_y
if number ==1
A(k,mask_B(i-1,j)-1)=1;
A(k,mask_B(i,j-1)-1)=1;
A(k,mask_B(i,j+1)-1)=1;
A(k,mask_B(i+1,j)-1)=1;
A(k,mask_B(i,j)-1)=-4;
end
k=k+1;
end
end
end
%%
%求散度,将B补充完全
[A_hxb,A_lxb,~]=find(mask_A==0);
min_Ax=min(A_hxb);
min_Ay=min(A_lxb);
max_Ax=max(A_hxb);
max_Ay=max(A_lxb);
k=1;
for i=min_Ax:max_Ax
for j=min_Ay:max_Ay
if i==min_Ax||i==max_Ax||j==min_Ay||j==max_Ay
k=k+1;
continue;
end
B(k)=image_A(i-1,j)+image_A(i,j-1)+image_A(i,j+1)+image_A(i+1,j)-4*image_A(i,j);%非边界点B为散度
k=k+1;
end
end
number=number+1;
end
图像泊松融合 主函数 main.m
%%图像泊松融合
clc,clear
close all
%a是融合的小图像 %b是背景文件
a=double(imread('4.jpg'));
b=double(imread('1.jpg'));
[row_a,col_a,g_a]=size(a);%size()返回矩阵行、列、g_a=3表示rgb,g_a=1表示灰度图
[row_b,col_b,g_b]=size(b);
mask_A=zeros(row_a,col_a);%创建和原图一样大小的零矩阵
imshow(uint8(b));
flat=1;
while flat==1
%法1 鼠标选择位置
[y_start,x_start]=ginput(1);%获得1个鼠标点击位置
%法2 输入位置数据
%x_start=100;y_start=10; %输入坐标(10,100)输入顺序Y,X
x_end=x_start+row_a-1;
y_end=y_start+col_a-1;
flat=0;
if x_end>row_b||y_end>col_b
disp('Array out of line'); %融合小图像出界,错误提示
flat=1;
end
end
mask_B=ones(row_b,col_b);%创建和背景图像一样大小的全1矩阵
mask_B(x_start:x_end,y_start:y_end)=0;%将融入小图像位置部分置0(黑色)
global number %全局变量
number=1;
%%
[A,B]=create_AB(a(:,:,1),mask_A,b(:,:,1),mask_B); %红色通道
x_R= A\B;
%%
[~,B]=create_AB(a(:,:,2),mask_A,b(:,:,2),mask_B);%绿色通道
x_G= A\B;
%%
[~,B]=create_AB(a(:,:,3),mask_A,b(:,:,3),mask_B);%蓝色通道
x_B= A\B;
%%
[hxb,lxb,l]=find(mask_B==0);%find(A)找到矩阵A非零元素下标,返回行号列号取值
%matlab按列存储
s=[hxb';lxb'];
[s1,id1]=sort(s(1,:)); %对s第一行元素排序
s_z=[s1;s(2,id1)];
hxb=s_z(1,:);
lxb=s_z(2,:);
for i=1:length(l)
b(hxb(i),lxb(i),1)=x_R(i);
b(hxb(i),lxb(i),2)=x_G(i);
b(hxb(i),lxb(i),3)=x_B(i);
end
imshow(uint8(b))
视频帧直接融合
主函数 main.m
%%此代码意在将小视频融合入原视频
%步骤:
% 1.读取小视频帧、原视频帧
% 2.进行泊松融合
% 3.将融合视频帧组成融合视频
%%
clc
clear
close all;
% addpath(fullfile(pwd, 'picture_ronghe'));
%读取原视频文件
[fastaFile,dirName]=uigetfile({'*.avi;*.mp4;*.rmvb;*.wmv','Video File(*.avi;*.mp4;*.rmvb;*.wmv)';...
'*.*', 'All Files (*.*)'}, ...
'Choose a Video File');
[~, name] = fileparts([dirName,fastaFile]);
vid = VideoReader([dirName,fastaFile]);
vid_numFrames = vid.NumFrames;
vid_Frame = read(vid, 1);imshow(vid_Frame),title('第一帧')
%读取放大后的视频
[fastaFile,dirName]=uigetfile({'*.avi;*.mp4;*.rmvb;*.wmv','Video File(*.avi;*.mp4;*.rmvb;*.wmv)';...
'*.*', 'All Files (*.*)'}, ...
'Choose a Video File');
[~, name2] = fileparts([dirName,fastaFile]);
vidAmp = VideoReader([dirName,fastaFile]);
vidAmp_numFrames = vidAmp.NumFrames;
outName = fullfile(dirName,[name '_ronghe.avi']);
vidOut = VideoWriter(outName);
vidOut.FrameRate = vid.FrameRate;
open(vidOut)
tic %tic toc 联合使用,用于计时
%法1 鼠标选择位置
[y_start,x_start]=ginput(1);%获得1个鼠标点击位置
%法2 输入位置数据
%x_start=100;y_start=10; %输入坐标(10,100)输入顺序 先Y后X
for i = 1 : min(vid.NumFrames,vidAmp.NumFrames)
% for i = 1 : 20
Frame = read(vid, i);%原视频帧
FrameAmp = read(vidAmp, i);%放大视频帧
integration = main_cc2( Frame, FrameAmp,y_start,x_start); %输入顺序 Y,X
writeVideo(vidOut,im2uint8(integration));
end
close(vidOut);
toc
fprintf('视频融合完成\n');
调用函数 main_cc2
function I=main_cc2(I,a,y_start,x_start)
close all
a=double(a);
I=double(I);
[row_a,col_a,~]=size(a);%目标文件%放大后的视频帧
[row_b,col_b,~]=size(I);%背景文件%原视频帧
mask_A=zeros(row_a,col_a);
imshow(uint8(I));
x_end=x_start+row_a-1;
y_end=y_start+col_a-1;
mask_B=ones(row_b,col_b);
mask_B(x_start:x_end,y_start:y_end)=0;
global number
number=1;
%%
[A,B]=create_AB(a(:,:,1),mask_A,I(:,:,1),mask_B);
x_R= A\B;
%%
[~,B]=create_AB(a(:,:,2),mask_A,I(:,:,2),mask_B);
x_G= A\B;
%%
[~,B]=create_AB(a(:,:,3),mask_A,I(:,:,3),mask_B);
x_B= A\B;
%%
[hxb,lxb,l]=find(mask_B==0);%他是按照一列列进行遍历的
s=[hxb';lxb'];
[s1,id1]=sort(s(1,:));
s_z=[s1;s(2,id1)];
hxb=s_z(1,:);
lxb=s_z(2,:);
for i=1:length(l)
I(hxb(i),lxb(i),1)=x_R(i);
I(hxb(i),lxb(i),2)=x_G(i);
I(hxb(i),lxb(i),3)=x_B(i);
end
% imshow(uint8(I))
I =uint8(I);
end
调用函数 create_AB
function [A,B]=create_AB(image_A,mask_A,image_B,mask_B)
%假设插入的图片为方形
%image_A为插入图片
%mask_A为背景图片的模子,待插入部分为0,不插入部分为1
global number
[hxb,lxb,~]=find(mask_B==0);
B=zeros(length(hxb),1);%创建B
s=[hxb';lxb'];
[s1,id1]=sort(s(1,:));
s_z=[s1;s(2,id1)];%将行下标和列下标的顺序整理为行优先
hxb=s_z(1,:);
lxb=s_z(2,:);
min_x=min(hxb);
min_y=min(lxb);
max_x=max(hxb);
max_y=max(lxb);
k=2;
for i=1:length(hxb)
mask_B(hxb(i),lxb(i))=k;
k=k+1;
end
if number==1
A=sparse(zeros(length(hxb),length(hxb)));
end
if number~=1
A=0;
end
k=1;%k为正在填写A矩阵的第k行
for i=min_x:max_x
for j=min_y:max_y
if i==min_x||i==max_x||j==min_y||j==max_y
if number==1%如果第一次运行该求A函数
A(k,k)=1;
end
B(k)=image_B(i,j);%边界点B为其像素值
k=k+1;
end
if i~=min_x && i~=max_x&&j~=min_y&&j~=max_y
if number ==1
A(k,mask_B(i-1,j)-1)=1;
A(k,mask_B(i,j-1)-1)=1;
A(k,mask_B(i,j+1)-1)=1;
A(k,mask_B(i+1,j)-1)=1;
A(k,mask_B(i,j)-1)=-4;
end
k=k+1;
end
end
end
%%
%求散度,将B补充完全
[A_hxb,A_lxb,~]=find(mask_A==0);
min_Ax=min(A_hxb);
min_Ay=min(A_lxb);
max_Ax=max(A_hxb);
max_Ay=max(A_lxb);
k=1;
for i=min_Ax:max_Ax
for j=min_Ay:max_Ay
if i==min_Ax||i==max_Ax||j==min_Ay||j==max_Ay
k=k+1;
continue;
end
B(k)=image_A(i-1,j)+image_A(i,j-1)+image_A(i,j+1)+image_A(i+1,j)-4*image_A(i,j);%非边界点B为散度
k=k+1;
end
end
number=number+1;
end
关于图片直接融合,还有一种方法,用imshow()函数
先显示大图片做背景,再hold on ,在背景图上直接显示小图片,然后保存当前figure
即可
%axes 限制坐标轴范围
xiao=axes('Position',[0.26,0.26,0.35,0.38]);
imshow ('1.jpg');hold on
axes(xiao);
imshow ('4.jpg');
%保存当前figure图像
Frame=getframe;
imwrite(Frame.cdata,'11.jpg');