1.8 MiB
1.8 MiB
!pip install torch_snippets
from torch_snippets import *
# feature_extractor = 'orb'
# feature_matching = 'bf'
Collecting torch_snippets Downloading https://files.pythonhosted.org/packages/d6/56/1093531de48ccc64410a480def65c386d18c981cfac21e7e3f92c9496352/torch_snippets-0.228-py3-none-any.whl Collecting loguru [?25l Downloading https://files.pythonhosted.org/packages/6d/48/0a7d5847e3de329f1d0134baf707b689700b53bd3066a5a8cfd94b3c9fc8/loguru-0.5.3-py3-none-any.whl (57kB) [K |████████████████████████████████| 61kB 2.8MB/s [?25hRequirement already satisfied: Pillow in /usr/local/lib/python3.6/dist-packages (from torch_snippets) (7.0.0) Requirement already satisfied: matplotlib in /usr/local/lib/python3.6/dist-packages (from torch_snippets) (3.2.2) Collecting opencv-python-headless [?25l Downloading https://files.pythonhosted.org/packages/e2/e2/6670da2b12544858657058a5db2f088a18c56d0144bef8d178ad4734b7a3/opencv_python_headless-4.4.0.44-cp36-cp36m-manylinux2014_x86_64.whl (36.7MB) [K |████████████████████████████████| 36.7MB 1.3MB/s [?25hRequirement already satisfied: tqdm in /usr/local/lib/python3.6/dist-packages (from torch_snippets) (4.41.1) Requirement already satisfied: dill in /usr/local/lib/python3.6/dist-packages (from torch_snippets) (0.3.2) Requirement already satisfied: pandas in /usr/local/lib/python3.6/dist-packages (from torch_snippets) (1.1.2) Requirement already satisfied: numpy in /usr/local/lib/python3.6/dist-packages (from torch_snippets) (1.18.5) Collecting aiocontextvars>=0.2.0; python_version < "3.7" Downloading https://files.pythonhosted.org/packages/db/c1/7a723e8d988de0a2e623927396e54b6831b68cb80dce468c945b849a9385/aiocontextvars-0.2.2-py2.py3-none-any.whl Requirement already satisfied: kiwisolver>=1.0.1 in /usr/local/lib/python3.6/dist-packages (from matplotlib->torch_snippets) (1.2.0) Requirement already satisfied: cycler>=0.10 in /usr/local/lib/python3.6/dist-packages (from matplotlib->torch_snippets) (0.10.0) Requirement already satisfied: python-dateutil>=2.1 in /usr/local/lib/python3.6/dist-packages (from matplotlib->torch_snippets) (2.8.1) Requirement already satisfied: pyparsing!=2.0.4,!=2.1.2,!=2.1.6,>=2.0.1 in /usr/local/lib/python3.6/dist-packages (from matplotlib->torch_snippets) (2.4.7) Requirement already satisfied: pytz>=2017.2 in /usr/local/lib/python3.6/dist-packages (from pandas->torch_snippets) (2018.9) Collecting contextvars==2.4; python_version < "3.7" Downloading https://files.pythonhosted.org/packages/83/96/55b82d9f13763be9d672622e1b8106c85acb83edd7cc2fa5bc67cd9877e9/contextvars-2.4.tar.gz Requirement already satisfied: six in /usr/local/lib/python3.6/dist-packages (from cycler>=0.10->matplotlib->torch_snippets) (1.15.0) Collecting immutables>=0.9 [?25l Downloading https://files.pythonhosted.org/packages/99/e0/ea6fd4697120327d26773b5a84853f897a68e33d3f9376b00a8ff96e4f63/immutables-0.14-cp36-cp36m-manylinux1_x86_64.whl (98kB) [K |████████████████████████████████| 102kB 10.4MB/s [?25hBuilding wheels for collected packages: contextvars Building wheel for contextvars (setup.py) ... [?25l[?25hdone Created wheel for contextvars: filename=contextvars-2.4-cp36-none-any.whl size=7666 sha256=f8a165c3ac2b22ad80f61738b271ef93036c96cd11af1335186f06598bb97516 Stored in directory: /root/.cache/pip/wheels/a5/7d/68/1ebae2668bda2228686e3c1cf16f2c2384cea6e9334ad5f6de Successfully built contextvars Installing collected packages: immutables, contextvars, aiocontextvars, loguru, opencv-python-headless, torch-snippets Successfully installed aiocontextvars-0.2.2 contextvars-2.4 immutables-0.14 loguru-0.5.3 opencv-python-headless-4.4.0.44 torch-snippets-0.228
!wget https://www.dropbox.com/s/mfg1codtc2rue84/g1.png
!wget https://www.dropbox.com/s/4yhui8s1xjndavm/g2.png
--2020-10-05 17:11:49-- https://www.dropbox.com/s/mfg1codtc2rue84/g1.png Resolving www.dropbox.com (www.dropbox.com)... 162.125.5.1, 2620:100:601d:1::a27d:501 Connecting to www.dropbox.com (www.dropbox.com)|162.125.5.1|:443... connected. HTTP request sent, awaiting response... 301 Moved Permanently Location: /s/raw/mfg1codtc2rue84/g1.png [following] --2020-10-05 17:11:49-- https://www.dropbox.com/s/raw/mfg1codtc2rue84/g1.png Reusing existing connection to www.dropbox.com:443. HTTP request sent, awaiting response... 302 Found Location: https://uc5ae3b5e6d89a5d1f941a070eb5.dl.dropboxusercontent.com/cd/0/inline/BAtSVe1XsaaYz-dNUT8PucSdjy59J17P0-IX4lxNRncoz7CpXaFnCeJ_3ClhJ_xqjSaE8G_HWaraS8s184p7sjLBHHXf1_83whtDGgIVRo2edKrdQAlEKy5qjMY03HJmeZU/file# [following] --2020-10-05 17:11:49-- https://uc5ae3b5e6d89a5d1f941a070eb5.dl.dropboxusercontent.com/cd/0/inline/BAtSVe1XsaaYz-dNUT8PucSdjy59J17P0-IX4lxNRncoz7CpXaFnCeJ_3ClhJ_xqjSaE8G_HWaraS8s184p7sjLBHHXf1_83whtDGgIVRo2edKrdQAlEKy5qjMY03HJmeZU/file Resolving uc5ae3b5e6d89a5d1f941a070eb5.dl.dropboxusercontent.com (uc5ae3b5e6d89a5d1f941a070eb5.dl.dropboxusercontent.com)... 162.125.9.15, 2620:100:601d:15::a27d:50f Connecting to uc5ae3b5e6d89a5d1f941a070eb5.dl.dropboxusercontent.com (uc5ae3b5e6d89a5d1f941a070eb5.dl.dropboxusercontent.com)|162.125.9.15|:443... connected. HTTP request sent, awaiting response... 200 OK Length: 277132 (271K) [image/png] Saving to: ‘g1.png’ g1.png 100%[===================>] 270.64K --.-KB/s in 0.07s 2020-10-05 17:11:50 (3.86 MB/s) - ‘g1.png’ saved [277132/277132] --2020-10-05 17:11:50-- https://www.dropbox.com/s/4yhui8s1xjndavm/g2.png Resolving www.dropbox.com (www.dropbox.com)... 162.125.5.1, 2620:100:601f:1::a27d:901 Connecting to www.dropbox.com (www.dropbox.com)|162.125.5.1|:443... connected. HTTP request sent, awaiting response... 301 Moved Permanently Location: /s/raw/4yhui8s1xjndavm/g2.png [following] --2020-10-05 17:11:50-- https://www.dropbox.com/s/raw/4yhui8s1xjndavm/g2.png Reusing existing connection to www.dropbox.com:443. HTTP request sent, awaiting response... 302 Found Location: https://uc65628330652e93bcd853321184.dl.dropboxusercontent.com/cd/0/inline/BAuCQY7ifx2KBi0o8py2GUxyM83OvafOWPQ3dMQXD9Wn7FYLst90ueZBfgamB3FAxGpwSXkZM1pS-gztpoq7icc8Vg16vSaBkCymRK-48aZJj3-VwhY7sZMuNVXn4EyIcpA/file# [following] --2020-10-05 17:11:51-- https://uc65628330652e93bcd853321184.dl.dropboxusercontent.com/cd/0/inline/BAuCQY7ifx2KBi0o8py2GUxyM83OvafOWPQ3dMQXD9Wn7FYLst90ueZBfgamB3FAxGpwSXkZM1pS-gztpoq7icc8Vg16vSaBkCymRK-48aZJj3-VwhY7sZMuNVXn4EyIcpA/file Resolving uc65628330652e93bcd853321184.dl.dropboxusercontent.com (uc65628330652e93bcd853321184.dl.dropboxusercontent.com)... 162.125.9.15, 2620:100:601d:15::a27d:50f Connecting to uc65628330652e93bcd853321184.dl.dropboxusercontent.com (uc65628330652e93bcd853321184.dl.dropboxusercontent.com)|162.125.9.15|:443... connected. HTTP request sent, awaiting response... 200 OK Length: 330008 (322K) [image/png] Saving to: ‘g2.png’ g2.png 100%[===================>] 322.27K --.-KB/s in 0.07s 2020-10-05 17:11:53 (4.47 MB/s) - ‘g2.png’ saved [330008/330008]
queryImg = read('g1.png', 1)
queryImg_gray = read('g1.png')
trainImg = read('g2.png', 1)
trainImg_gray = read('g2.png')
subplots([trainImg, queryImg], nc=2, figsize=(10,5), titles = ['Query image','Training image (Image to be stitched to Query image)'])
2020-10-05 17:11:53.215 | INFO | torch_snippets.loader:subplots:339 - plotting 2 images in a grid of 1x2 @ (10, 5)
# Fetch the keypoints and features corresponding to the images
descriptor = cv2.ORB_create()
kpsA, featuresA = descriptor.detectAndCompute(trainImg_gray, None)
kpsB, featuresB = descriptor.detectAndCompute(queryImg_gray, None)
# Draw the keypoints obtained on images
img_kpsA = cv2.drawKeypoints(trainImg_gray,kpsA,None,color=(0,255,0))
img_kpsB = cv2.drawKeypoints(queryImg_gray,kpsB,None,color=(0,255,0))
subplots([img_kpsB, img_kpsA], nc=2, figsize=(10,5), titles=['Query image with keypoints','Training image with keypoints'])
2020-10-05 17:11:53.638 | INFO | torch_snippets.loader:subplots:339 - plotting 2 images in a grid of 1x2 @ (10, 5)
bf = cv2.BFMatcher(cv2.NORM_HAMMING)
best_matches = bf.match(featuresA,featuresB)
matches = sorted(best_matches, key = lambda x:x.distance)
img3 = cv2.drawMatches(trainImg,kpsA,queryImg,kpsB,matches[:100], None,flags=cv2.DrawMatchesFlags_NOT_DRAW_SINGLE_POINTS)
show(img3)
kpsA = np.float32([kp.pt for kp in kpsA])
kpsB = np.float32([kp.pt for kp in kpsB])
ptsA = np.float32([kpsA[m.queryIdx] for m in matches])
ptsB = np.float32([kpsB[m.trainIdx] for m in matches])
(H, status) = cv2.findHomography(ptsA, ptsB, cv2.RANSAC,4)
width = trainImg.shape[1] + queryImg.shape[1]
height = trainImg.shape[0] + queryImg.shape[0]
result = cv2.warpPerspective(trainImg, H, (width, height))
result[0:queryImg.shape[0], 0:queryImg.shape[1]] = queryImg
_x = np.nonzero(result.sum(0).sum(-1) == 0)[0][0]
_y = np.nonzero(result.sum(1).sum(-1) == 0)[0][0]
show(result[:_y,:_x])