Advertisement
yckao85

多媒體導論 affine 小考 Q2

Apr 23rd, 2018
114
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 3.49 KB | None | 0 0
  1. from numpy import linalg
  2. from skimage import io
  3. import numpy as np
  4.  
  5. ''' split rect area by given points
  6.     ex. [0,0], [1, 2], [5, 5]
  7.     [[0, 0], [1, 0], [1, 2]],
  8.     [[1, 0], [5, 0], [5, 2]],
  9.     [[0, 2], [1, 2], [1, 5]],
  10.     [[1, 2], [5, 2], [5, 5]]
  11.     (4 area)
  12. '''
  13. def split_area_by_point(points):
  14.     sorted_x = list(map(lambda p : p[0],sorted(points, key = lambda p : p[0])))
  15.     sorted_y = list(map(lambda p : p[1],sorted(points, key = lambda p : p[1])))
  16.     areas = []
  17.     for y in range(0, len(sorted_y) - 1):
  18.         for x in range(0, len(sorted_x) - 1):
  19.             areas.append([[sorted_x[x], sorted_y[y]], [sorted_x[x+1], sorted_y[y]], [sorted_x[x+1], sorted_y[y+1]]])
  20.     return areas
  21.  
  22. '''
  23. solve a, b in y = ax + b
  24. '''
  25. def solve(src_points, dst_points):
  26.     x = [
  27.         [src_points[0][0], src_points[0][1], 0, 0, 1, 0],
  28.         [0, 0, src_points[0][0], src_points[0][1], 0, 1],
  29.         [src_points[1][0], src_points[1][1], 0, 0, 1, 0],
  30.         [0, 0, src_points[1][0], src_points[1][1], 0, 1],
  31.         [src_points[2][0], src_points[2][1], 0, 0, 1, 0],
  32.         [0, 0, src_points[2][0], src_points[2][1], 0, 1],
  33.     ]
  34.    
  35.     y = [
  36.         [dst_points[0][0]],
  37.         [dst_points[0][1]],
  38.         [dst_points[1][0]],
  39.         [dst_points[1][1]],
  40.         [dst_points[2][0]],
  41.         [dst_points[2][1]]
  42.     ]
  43.     res = linalg.solve(x, y)
  44.     return {'a': res[:4].reshape(2,2), 'b': res[4:]}
  45.    
  46. ''' transform y = ax + b '''
  47. def linearTransform(point, transform):
  48.     ''' calculate result '''
  49.     [[res_x], [res_y]] = np.rint(np.dot(transform['a'], [[point[0]], [point[1]]]) + transform['b']).astype(int)
  50.     return [res_x, res_y]
  51.    
  52. ''' transform x = a^-1(y-b) '''
  53. def linearTransformInv(point, transform):
  54.     ''' calculate inverse matrix '''
  55.     inv = linalg.inv(transform['a'])
  56.     ''' calculate result '''
  57.     [[res_x], [res_y]] = np.rint(np.dot(inv, ([[point[0]], [point[1]]] - transform['b']))).astype(int)
  58.     return [res_x, res_y]
  59.    
  60. ''' up_sampling '''
  61. def up_sampling(src_img, dst_img, transform, area):
  62.     ''' calculate destination area '''
  63.     dst_area = [linearTransform(area[0], transform), linearTransform(area[2], transform)]
  64.     ''' loop in destination area'''
  65.     for dst_y in np.arange(dst_area[0][1], dst_area[1][1]):
  66.         for dst_x in np.arange(dst_area[0][0], dst_area[1][0]):
  67.             ''' calculate original point '''
  68.             [x, y] = linearTransformInv([dst_x, dst_y], transform)
  69.             dst_img[dst_y][dst_x] = src_img[y][x]
  70.     return dst_img
  71.  
  72. ''' define path and name '''
  73. path = '/Users/yckao85/Desktop/node_quick/'
  74. src_name = '000044.jpg'
  75. dst_name = 'destination.jpg'
  76.  
  77. ''' read file and generate black result '''
  78. src_img = io.imread(path + src_name)
  79. dst_img = np.zeros(src_img.shape)
  80.  
  81.  
  82. ''' get width and height '''
  83. width = src_img.shape[1]
  84. height = src_img.shape[0]
  85.  
  86. ''' pack source points '''
  87. src_points = [
  88.     [0, 0],
  89.     [830, 630],
  90.     [1595, 1760],
  91.     [1100, 1050],
  92.     [1340, 1430],
  93.     [width, height]
  94. ]
  95.  
  96. ''' pack destination points '''
  97. dst_points = [
  98.     [0, 0],
  99.     [200, 200],
  100.     [(width / 2 - 200) / 2, (height / 2 - 200) / 2],
  101.     [width - (width / 2 - 200) / 2, height - (height / 2 - 200) / 2],
  102.     [width - 200, height - 200],
  103.     [width, height]
  104. ]
  105.  
  106.  
  107. ''' generate areas '''
  108. src_areas = split_area_by_point(src_points)
  109. dst_areas = split_area_by_point(dst_points)
  110.  
  111. ''' generate transforms '''
  112. transforms = []
  113. for i in range(0, len(src_areas)):
  114.     transforms.append(solve(src_areas[i], dst_areas[i]))
  115.  
  116. ''' sampling new image'''
  117. for i in range(0, len(src_areas)):
  118.     print(i + 1, '/', len(src_areas))
  119.     dst_img = up_sampling(src_img, dst_img, transforms[i], src_areas[i])
  120.  
  121. ''' save '''
  122. io.imsave(path + dst_name, dst_img.astype(np.uint8))
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement