2

I am trying to convert c++ opencv cv2.remap code to python. I am not getting any error but result is not as expected.I am getting zoomed image

c++ code

int main()
{
    Mat img = imread("captcha1.jpg");
    float phase = -0.8 * CV_PI;
    float omega = 2.0 * CV_PI / img.cols;
    float amp = 15;
    Mat_<Vec2f> proj(img.size());
    for (int y=0; y<img.rows; y++) {
        for (int x=0; x<img.cols; x++) {
            float u = 0;
            float v = sin(phase + float(x) * omega) * amp;
            proj(y,x) = Vec2f(float(x) + u, float(y) + v);
        }
    }
    Mat corr;
    cv::remap(img, corr, proj, cv::Mat(), INTER_LINEAR);
    imshow("in",img);
    imshow("out",corr);
    waitKey();
}

python code :

from __future__ import print_function
import cv2
import numpy as np
from past.builtins import xrange
def update():
   for j in xrange(rows):
        for i in xrange(cols):

            phase = -0.8 * np.pi
            omega = 2.0 * np.pi / cols
            amp = 15
            u = -100
            v = np.sin(phase + float(i) * omega) * amp
            value_xy = (float(i) + u) + (float(j) + v)
            map_x.itemset((j, i), value_xy)
            map_y.itemset((j, i), 0)

img = cv2.imread('test.jpg')
map_x = np.zeros(img.size, np.float32)
map_y = np.zeros(img.shape[:2], np.float32)
rows, cols = img.shape[:2]
update()
dst = cv2.remap(img, map_x, map_y, cv2.INTER_LINEAR)
cv2.imshow('dst', dst)
cv2.waitKey(0)
cv2.destroyAllWindows()

Original image :

enter image description here

C++ Result :

enter image description here

Python result:

enter image description here

Jeya Kumar
  • 1,002
  • 1
  • 13
  • 36
  • 2
    Why `u = 0` in c++ and `u = -100` in Python? Why not pass `rows, cols` to `update` as parameters, rather then relying on global variables? IMHO `map_y` can just be `None`. – Dan Mašek Sep 22 '18 at 22:50
  • 2
    I also don't understand why you make your life harder by changing variable names and the structure of the code when there's absolutely no reason for it. I mean, look at [this](https://pastebin.com/bCXtMMVM) -- isn't that easier to compare side-by-side with the original C++ implementation? – Dan Mašek Sep 22 '18 at 23:14
  • 2
    Once you have that, you can try to optimize things. e.g. get rid of those nested `for` loops, and replace them with vectorized `numpy` operations. Say, [like this](https://pastebin.com/zXNW1gE5) – Dan Mašek Sep 22 '18 at 23:36
  • @DanMašek : Thanks for the help, confused on this # NB: Mat_ -> 2 channels proj = np.zeros((img.shape[0], img.shape[1], 2), np.float32) – Jeya Kumar Sep 23 '18 at 04:32

1 Answers1

5

This is my result:

enter image description here

Generaly, I prefer the the vectorized implementation to the for-loop implementation in Python. Here is my code:

#!/usr/bin/python3
# 2018.09.23 12:24 (CST)
import cv2 
import numpy as np 

fname = "remap.jpg"
img = cv2.imread(fname)
nh, nw = img.shape[:2]

PI = 3.141592653589793
phase = -0.8 * PI
omega = 2.0 * PI / nw
amp = 15

xs, ys = np.meshgrid(np.arange(0, nw), np.arange(0, nh))
ys = np.sin(phase+xs*omega)*amp + ys
xs = np.float32(xs)
ys = np.float32(ys)

dst= cv2.remap(img, xs, ys, cv2.INTER_CUBIC)
cv2.imwrite("dst.png", dst)
Kinght 金
  • 17,681
  • 4
  • 60
  • 74