How to add a portion of image to another image

28 vues (au cours des 30 derniers jours)
Mohamed Elbeialy
Mohamed Elbeialy le 27 Août 2020
Réponse apportée : DGM le 20 Jan 2023
How to add different portion of flower's image to car's image

Réponses (3)

Image Analyst
Image Analyst le 27 Août 2020
See my attached copy and paste demos.
  3 commentaires
Image Analyst
Image Analyst le 27 Août 2020
You did not show us what you want. Do you want to PASTE the flower image onto the car image, or ADD it to the car image (so you'll see both flower and car pixels blended). Please post what you want to obtain.
Mohamed Elbeialy
Mohamed Elbeialy le 27 Août 2020
Just add various pixels of flower's image into car's image to be one image. This part should be same size and pasted at top and bottom of car's image

Connectez-vous pour commenter.


Image Analyst
Image Analyst le 27 Août 2020
Try this. It will add the smaller image to the lower right part of the larger image.
% Initialization steps.
clc; % Clear the command window.
close all; % Close all figures (except those of imtool.)
clear; % Erase all existing variables. Or clearvars if you want.
workspace; % Make sure the workspace panel is showing.
format long g;
format compact;
fontSize = 20;
rgbImage1 = imread('car.jpeg');
subplot(2, 2, 1);
imshow(rgbImage1);
[rows1, columns1, numberOfColorChannels1] = size(rgbImage1)
title('Image 1', 'FontSize', fontSize);
impixelinfo;
rgbImage2 = imread('pink flower.jpeg');
subplot(2, 2, 2);
imshow(rgbImage2);
[rows2, columns2, numberOfColorChannels2] = size(rgbImage2)
title('Image 2', 'FontSize', fontSize);
impixelinfo;
% Find out where the smaller flower image needs to be so that
% it will be in the lower right corner of the larger car image.
row3 = abs(rows1 - rows2) + 1
column3 = abs(columns1 - columns2) + 1
% Add them
sumImage = rgbImage1; % Initialize
subplot(2, 2, 3:4);
imshow(sumImage);
v = (double(rgbImage1(row3:end, column3:end, :)) + double(rgbImage2)) / 2;
sumImage(row3:end, column3:end, :) = uint8((double(rgbImage1(row3:end, column3:end, :)) + double(rgbImage2)) / 2);
subplot(2, 2, 3:4);
imshow(sumImage);
title('Image 1 + Image 2', 'FontSize', fontSize);
impixelinfo;

DGM
DGM le 20 Jan 2023
Hmm. That's a very good question. How would one accomplish an ill-defined image composition? Well, the answer is easy. You could just guess until you get tired. What are our requirements?
  • add "different portion" of flower image to car image
  • add "various pixels" of flower image into car image
  • should be same size and pasted at top and bottom of car image
For these superfluous examples, I've decided to emphasize the ridiculousness by actively avoiding MIMT conveniences. The result is a wall of code.
Let's start with a simple, but improbable interpretation.
% "various" must mean "all pixels"
% "pasted at top and bottom" must mean "concatenated"
% "same size" must mean "cannot be resized to match BG width"
% images come from somewhere
FG = imread('flowersmall.jpg');
BG = imread('carsmall.jpg');
szfg = size(FG);
szbg = size(BG);
% pad FG to match BG width
padsize = (szbg(2)-szfg(2))/2;
FG = padarray(FG,[0 floor(padsize)],0,'pre');
FG = padarray(FG,[0 ceil(padsize)],0,'post');
% concatenate
BG = [FG; BG; FG];
imshow(BG)
Is this more or less probable?
% "various" must mean "random"
% "pasted at top and bottom" must mean "inserted near image edges"
% images come from somewhere
FG = imread('flowersmall.jpg');
BG = imread('carsmall.jpg');
szfg = size(FG);
szbg = size(BG);
% get "various pixels" from foreground
N = 10E3;
idx = randi([1 prod(szfg(1:2))],N,1);
idx = idx + (0:2)*prod(szfg(1:2));
FGroi = FG(idx);
% insert selected pixels into top/bottom of background
yidx = 20*randn(N,1);
yidx = mod(round(yidx)+1,szbg(1))+1;
xidx = randi([1 szbg(2)],N,1);
idx = sub2ind(szbg(1:2),yidx,xidx) + (0:2)*prod(szbg(1:2));
BG(idx) = FGroi;
imshow(BG)
Uh or maybe ... ?
% "various" must mean "random"
% "pasted at top and bottom" must mean "inserted above/below the car object"
% images come from somewhere
FG = imread('flowersmall.jpg');
BG = imread('carsmall.jpg');
szfg = size(FG);
szbg = size(BG);
% get "various pixels" from foreground
N = 10E3;
idx = randi([1 prod(szfg(1:2))],N,1);
idx = idx + (0:2)*prod(szfg(1:2));
FGroi = FG(idx);
% insert selected pixels above/below car
carmk = imread('carsmallmask.png');
valididx = find(any(carmk,1) & ~carmk);
idx = valididx(randperm(numel(valididx)));
idx = idx(1:N) + (0:2)*prod(szbg(1:2));
BG(idx) = FGroi;
imshow(BG)
No wait, I know!
% "various" must mean "random"
% "pasted at top and bottom" must mean "appended to image edges"
% "same size" must mean "same width as BG"
% images come from somewhere
FG = imread('flowersmall.jpg');
BG = imread('carsmall.jpg');
szfg = size(FG);
szbg = size(BG);
% get "various pixels" from foreground
N = 10E3;
N = round(N/szbg(2))*szbg(2);
idx = randi([1 prod(szfg(1:2))],N,1);
idx = idx + (0:2)*prod(szfg(1:2));
FGroi = FG(idx);
% append selected pixels to bg edges
FGroi = reshape(FGroi,[],szbg(2),3);
toppad = FGroi(1:floor(size(FGroi,1)/2),:,:);
botpad = FGroi(1:ceil(size(FGroi,1)/2),:,:);
BG = [toppad; BG; botpad];
imshow(BG)
Okay, okay. Maybe "random" isn't really a plausible interpretation any way you cut it. Let's try something else.
% "various" must mean "the flower itself"
% "pasted at top and bottom" must mean "inserted above/below the car object"
% "same size" must mean "without altering the scale of the flower"
% images come from somewhere
FG = imread('flowersmall.jpg');
BG = imread('carsmall.jpg');
% some masks were created
carmk = imread('carsmallmask.png');
flowmk = imread('flowersmallmask.png');
% crop FG
fos = 15;
FG = FG(fos:end,:,:);
flowmk = flowmk(fos:end,:,:);
szfg = size(FG);
% get ROI subscript vectors
os = [0 25];
xidx = os(2)+1:os(2)+szfg(2);
yidx = os(1)+1:os(1)+szfg(1);
% extract background region where FG is located
% compose everything
% gosh this sure is cumbersome and verbose.
% if only there were a better way. oh well :(
BGroi = im2double(BG(yidx,xidx,:));
FG = im2double(FG);
flowmk = im2double(flowmk);
carmk = im2double(carmk(yidx,xidx));
Rroi = flowmk.*FG + (1-flowmk).*BGroi;
Rroi = carmk.*BGroi + (1-carmk).*Rroi;
Rroi = im2uint8(Rroi);
% insert result back into background
BG(yidx,xidx,:) = Rroi;
imshow(BG)
Or maybe you want something ... fancier?
% "various" must mean "the flower itself"
% "pasted at top and bottom" must mean "inserted near image edges"
% "same size" must mean "without altering the scale of the flower"
% images come from somewhere
FG = imread('flowersmall.jpg');
BG = imread('carsmall.jpg');
szbg = size(BG);
% create asymmetric linear vignette mask
r = [1 max(szbg(1:2))/min(szbg(1:2))];
xx = 1:szbg(2);
yy = (1:szbg(1)).';
c = round(szbg/2);
Dmask = sqrt(((xx-c(2))/r(2)).^2 + ((yy-c(1))/r(1)).^2);
Dmask = mat2gray(Dmask);
% apply soft vignette
thiscolor = [0.9928 0.6433 0.8056];
Dmask = imadjust(Dmask,[0.2 1],[0 1],1.1);
BG = im2double(BG);
BG = Dmask.*permute(thiscolor,[1 3 2]) + (1-Dmask).*BG;
% apply spots of two different sizes
thiscolor = [0.9555 0.8095 0.8963];
fk = createsoftcircle(10);
spotmk = imnoise(zeros(szbg(1:2)),'salt & pepper',0.001);
spotmk = mat2gray(imfilter(spotmk,fk)).*Dmask;
BG = spotmk.*permute(thiscolor,[1 3 2]) + (1-spotmk).*BG;
fk = createsoftcircle(5);
spotmk = imnoise(zeros(szbg(1:2)),'salt & pepper',0.001);
spotmk = mat2gray(imfilter(spotmk,fk)).*Dmask;
BG = spotmk.*permute(thiscolor,[1 3 2]) + (1-spotmk).*BG;
% some masks were created
flowmk = imread('flowersmallmask.png');
% crop FG
fos = [80 100];
thisFG = FG(1:end-fos(1)+1,fos(2):end,:);
thisflowmk = flowmk(1:end-fos(1)+1,fos(2):end,:);
szfg = size(thisFG);
% get ROI subscript vectors
xidx = 1:szfg(2);
yidx = szbg(1)-szfg(1)+1:szbg(1);
% extract background region where FG is located, compose
BGroi = BG(yidx,xidx,:);
thisFG = im2double(thisFG);
thisflowmk = im2double(thisflowmk);
Rroi = thisflowmk.*thisFG + (1-thisflowmk).*BGroi;
% insert result back into background
BG(yidx,xidx,:) = Rroi;
% crop FG
fos = [100 100];
thisFG = FG(fos(1):end,1:end-fos(2)+1,:);
thisflowmk = flowmk(fos(1):end,1:end-fos(2)+1,:);
szfg = size(thisFG);
% get ROI subscript vectors
xidx = szbg(2)-szfg(2)+1:szbg(2);
yidx = 1:szfg(1);
% do it again
BGroi = BG(yidx,xidx,:);
thisFG = im2double(thisFG);
thisflowmk = im2double(thisflowmk);
Rroi = thisflowmk.*thisFG + (1-thisflowmk).*BGroi;
% insert result back into background
BG(yidx,xidx,:) = Rroi;
BG = im2uint8(BG);
imshow(BG)
function fk = createsoftcircle(r)
xx = 1:2*r+1;
yy = (1:2*r+1).';
fk = sqrt((xx-r+1).^2 + (yy-r+1).^2);
fk = min(max(-(fk-r)/2,0),1);
end
Hmm. Yeah, that's probably it. In hindsight, it's hard to imagine it any other way.

Produits


Version

R2019a

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by