Skip to content

Commit 796153c

Browse files
authored
first commit
1 parent ec7a542 commit 796153c

20 files changed

+1840
-0
lines changed

Diff for: HogDescriptor.py

+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
import cv2
2+
import matplotlib.pyplot as plt
3+
4+
import numpy as np
5+
6+
from skimage.feature import hog
7+
from skimage import data, color, exposure
8+
9+
class HogDescriptor:
10+
def describe_hog(self, image):
11+
image = color.rgb2gray(image)
12+
13+
fd, hog_image = hog(image, orientations=8, pixels_per_cell=(16, 16),
14+
cells_per_block=(1, 1), visualise=True)
15+
return fd
16+
17+

Diff for: HogDescriptor.pyc

1001 Bytes
Binary file not shown.

Diff for: app.py

+82
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
# http://flask.pocoo.org/docs/patterns/fileuploads/
2+
import os, glob
3+
import flask_search
4+
from flask import Flask, request, redirect, url_for, send_from_directory, jsonify, send_file, render_template
5+
from werkzeug import secure_filename
6+
import shutil
7+
8+
9+
UPLOAD_FOLDER = 'uploads'
10+
ALLOWED_EXTENSIONS = set(['txt', 'pdf', 'png', 'jpg', 'jpeg', 'gif','ppm'])
11+
12+
app = Flask(__name__)
13+
app.config['UPLOAD_FOLDER'] = UPLOAD_FOLDER
14+
15+
basedir = os.path.abspath(os.path.dirname(__file__))
16+
17+
def allowed_file(filename):
18+
# this has changed from the original example because the original did not work for me
19+
return filename[-3:].lower() in ALLOWED_EXTENSIONS
20+
21+
@app.route('/query', methods=['POST'])
22+
def upload_file():
23+
if request.method == 'POST':
24+
# check if the post request has the file part
25+
if 'file' not in request.files:
26+
print ('No file part')
27+
return redirect(request.url)
28+
print ("POST request", request.files)
29+
file = request.files['file']
30+
# if file and allowed_file(file.filename):
31+
if True:
32+
print '**found file', file.filename
33+
filename = secure_filename(file.filename)
34+
filepath = os.path.join(basedir, app.config['UPLOAD_FOLDER'], filename)
35+
file.save(filepath)
36+
result_from_search = flask_search.flask_search(filepath)
37+
38+
shutil.rmtree('query_images')
39+
os.mkdir('query_images')
40+
i = 9
41+
for _, res in result_from_search:
42+
shutil.copyfile('original1/'+ res, 'query_images/' +str(i)+ res)
43+
i = i-1
44+
# result_path = cd.function(file)
45+
# for browser, add 'redirect' function on top of 'url_for'
46+
# response = send_file(result_from_search[1])
47+
return jsonify(result_from_search)
48+
# return '''
49+
# <!doctype html>
50+
# <title>Upload new File</title>
51+
# <h1>Upload new File</h1>
52+
# <form action="" method=post enctype=multipart/form-data>
53+
# <p><input type=file name=file>
54+
# <input type=submit value=Upload>
55+
# </form>
56+
# '''
57+
return "Error in request processing"
58+
59+
@app.route('/')
60+
def home_page():
61+
files = [os.path.basename(x) for x in glob.glob('./query_images/*.png')]
62+
return render_template("home.html", urls=files)
63+
64+
@app.route('/result/<filename>')
65+
def uploaded_file(filename):
66+
return send_from_directory("query_images", filename)
67+
68+
@app.route('/hello', methods=['GET', 'POST'])
69+
def hello_world():
70+
print (request.method)
71+
if request.method == 'GET':
72+
var = "somethig"
73+
msg = "Hi!! you sent GET Req"
74+
return render_template('response.html', msg=msg)
75+
if request.method == 'POST':
76+
args = request.json
77+
print (args)
78+
msg = "Hi!! you sent POST Req"
79+
return msg
80+
81+
if __name__ == '__main__':
82+
app.run(debug=True, host='0.0.0.0')

Diff for: colordescriptor.py

+61
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
# import the necessary packages
2+
import numpy as np
3+
import cv2
4+
5+
class ColorDescriptor:
6+
def __init__(self, bins):
7+
# store the number of bins for the 3D histogram
8+
self.bins = bins
9+
10+
def describe(self, image):
11+
# convert the image to the HSV color space and initialize
12+
# the features used to quantify the image
13+
image = cv2.cvtColor(image, cv2.COLOR_BGR2HSV)
14+
features = []
15+
16+
# grab the dimensions and compute the center of the image
17+
(h, w) = image.shape[:2]
18+
(cX, cY) = (int(w * 0.5), int(h * 0.5))
19+
20+
# divide the image into four rectangles/segments (top-left,
21+
# top-right, bottom-right, bottom-left)
22+
segments = [(0, cX, 0, cY), (cX, w, 0, cY), (cX, w, cY, h),
23+
(0, cX, cY, h)]
24+
25+
# construct an elliptical mask representing the center of the
26+
# image
27+
(axesX, axesY) = (int(w * 0.75) / 2, int(h * 0.75) / 2)
28+
ellipMask = np.zeros(image.shape[:2], dtype = "uint8")
29+
cv2.ellipse(ellipMask, (cX, cY), (int(axesX), int(axesY)), 0, 0, 360, 255, -1)
30+
31+
# loop over the segments
32+
for (startX, endX, startY, endY) in segments:
33+
# construct a mask for each corner of the image, subtracting
34+
# the elliptical center from it
35+
cornerMask = np.zeros(image.shape[:2], dtype = "uint8")
36+
cv2.rectangle(cornerMask, (startX, startY), (endX, endY), 255, -1)
37+
cornerMask = cv2.subtract(cornerMask, ellipMask)
38+
39+
# extract a color histogram from the image, then update the
40+
# feature vector
41+
hist = self.histogram(image, cornerMask)
42+
features.extend(hist)
43+
44+
# extract a color histogram from the elliptical region and
45+
# update the feature vector
46+
hist = self.histogram(image, ellipMask)
47+
features.extend(hist)
48+
49+
# return the feature vector
50+
return features
51+
52+
def histogram(self, image, mask):
53+
# extract a 3D color histogram from the masked region of the
54+
# image, using the supplied number of bins per channel; then
55+
# normalize the histogram
56+
hist = cv2.calcHist([image], [0, 1, 2], mask, self.bins,
57+
[0, 180, 0, 256, 0, 256])
58+
hist = cv2.normalize(hist, hist).flatten()
59+
60+
# return the histogram
61+
return hist

Diff for: colordescriptor.pyc

1.85 KB
Binary file not shown.

Diff for: flask_search.py

+37
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
from colordescriptor import ColorDescriptor
2+
import numpy as np
3+
from pyimagesearch.zernikemoments import ZernikeMoments
4+
from HogDescriptor import HogDescriptor
5+
from hu import ShapeDescriptor
6+
from searcher import Searcher
7+
import argparse
8+
import cv2
9+
10+
def flask_search(image1):
11+
cd = HogDescriptor()
12+
# load the query image and describe it
13+
print ("before ", image1)
14+
image = cv2.imread(image1)
15+
print ("something ", image)
16+
image = (255 - image)
17+
image = cv2.resize(image, (256,256))
18+
query = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
19+
features = cd.describe_hog(query)
20+
21+
# perform the search
22+
# args['index'] is not defined
23+
searcher = Searcher('hog_index.csv')
24+
results = searcher.search(features)
25+
print (results)
26+
return results
27+
# display the query
28+
# cv2.imshow("Query", query)
29+
# print ("Reached here")
30+
# loop over the results
31+
# for (score, resultID) in results:
32+
# # load the result image and display it
33+
# result = cv2.imread(args["result_path"] + "/" + resultID)
34+
# path.extend(resultID)
35+
# #cv2.imshow("Result", result)
36+
# #cv2.waitKey(0)
37+
# return path

Diff for: flask_search.pyc

1.04 KB
Binary file not shown.

Diff for: hog_cropped.csv

+1,402
Large diffs are not rendered by default.

Diff for: hog_index.py

+40
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
# import the necessary packages
2+
from colordescriptor import ColorDescriptor
3+
from HogDescriptor import HogDescriptor
4+
import argparse
5+
6+
import glob
7+
import cv2
8+
9+
# construct the argument parser and parse the arguments
10+
ap = argparse.ArgumentParser()
11+
ap.add_argument("-d", "--dataset", required = True,
12+
help = "Path to the directory that contains the images to be indexed")
13+
ap.add_argument("-i", "--index", required = True,
14+
help = "Path to where the computed index will be stored")
15+
args = vars(ap.parse_args())
16+
17+
# initialize the Shape descriptor
18+
cd = HogDescriptor()
19+
20+
# open the output index file for writing
21+
output = open(args["index"], "w")
22+
23+
# use glob to grab the image paths and loop over them
24+
for imagePath in glob.glob(args["dataset"] + "/*.png"):
25+
# extract the image ID (i.e. the unique filename) from the image
26+
# path and load the image itself
27+
print ("Saving for image ", imagePath)
28+
imageID = imagePath[imagePath.rfind("/") + 1:]
29+
image = cv2.imread(imagePath)
30+
image = cv2.resize(image, (256, 256))
31+
32+
# describe the image
33+
features = cd.describe_hog(image)
34+
35+
# write the features to file
36+
features = [str(f) for f in features]
37+
output.write("%s,%s\n" % (imageID, ",".join(features)))
38+
39+
# close the index file
40+
output.close()

Diff for: hu.py

+21
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
2+
# import the necessary packages
3+
import numpy as np
4+
import cv2
5+
import argparse
6+
7+
class ShapeDescriptor:
8+
def describe1(self, image):
9+
# convert it to grayscale, and display it
10+
#gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
11+
image = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
12+
13+
#cv2.imshow("image", image)
14+
# extract Hu Moments from the image -- this list of numbers
15+
# is our 'feature vector' used to quantify the shape of the
16+
# object in our image
17+
features = cv2.HuMoments(cv2.moments(image)).flatten()
18+
# return the feature vector
19+
return features
20+
21+

Diff for: hu.pyc

697 Bytes
Binary file not shown.

Diff for: plot.py

+28
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
import sys
2+
import cv2
3+
import numpy as np
4+
import pylab as pl
5+
from sklearn.metrics import precision_recall_curve
6+
7+
recall=[0.0,0.1,0.2,0.3,0.4,0.5,0.6,0.7,0.8,0.9,1.0]
8+
precision=[1,1,1,1,1,1,1,1,1,1,1]
9+
def main(recall,precision,pr):
10+
pl.clf()
11+
12+
#for precision, recall, label in lines:
13+
f=pl.plot(recall, precision)
14+
pl.xlabel('Recall')
15+
pl.ylabel('Precision')
16+
pl.ylim([0.0, 2.5])
17+
pl.xlim([0.0, 1.0])
18+
pl.title('Precision-Recall')
19+
pl.legend(loc="upper right")
20+
#pl.show()
21+
pl.savefig(pr)
22+
img=cv2.imread(pr)
23+
cv2.imshow('pr',img)
24+
cv2.waitKey(0)
25+
cv2.destroyAllWindows()
26+
27+
28+
main(recall,precision,'pr_curve.tiff')

Diff for: pyimagesearch/__init__.pyc

151 Bytes
Binary file not shown.

Diff for: pyimagesearch/zernikemoments.py

+12
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
# import the necessary packages
2+
import mahotas
3+
4+
class ZernikeMoments:
5+
def __init__(self, radius):
6+
# store the size of the radius that will be
7+
# used when computing moments
8+
self.radius = radius
9+
10+
def describe(self, image):
11+
# return the Zernike moments for the image
12+
return mahotas.features.zernike_moments(image, self.radius)

Diff for: pyimagesearch/zernikemoments.pyc

804 Bytes
Binary file not shown.

Diff for: search.py

+64
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
# import the necessary packages
2+
from colordescriptor import ColorDescriptor
3+
import numpy as np
4+
from pyimagesearch.zernikemoments import ZernikeMoments
5+
from HogDescriptor import HogDescriptor
6+
from hu import ShapeDescriptor
7+
from searcher import Searcher
8+
import argparse
9+
import cv2
10+
11+
# construct the argument parser and parse the arguments
12+
ap = argparse.ArgumentParser()
13+
ap.add_argument("-i", "--index", required=True,
14+
help="Path to where the computed index will be stored")
15+
ap.add_argument("-q", "--query", required=True,
16+
help="Path to the query image")
17+
ap.add_argument("-r", "--result-path", required=True,
18+
help="Path to the result path")
19+
args = vars(ap.parse_args())
20+
21+
# initialize the image descriptor
22+
#cd = ShapeDescriptor()
23+
#cd = ZernikeMoments(50)
24+
cd = HogDescriptor()
25+
#cd = ColorDescriptor()
26+
# load the query image and describe it
27+
query = cv2.imread(args["query"])
28+
query = cv2.cvtColor(query, cv2.COLOR_BGR2GRAY)
29+
# pad the image with extra white pixels to ensure the
30+
# edges of the pokemon are not up against the borders
31+
# of the image
32+
#query = cv2.copyMakeBorder(query, 15, 15, 15, 15,
33+
# cv2.BORDER_CONSTANT, value = 255)
34+
35+
# invert the image and threshold it
36+
#thresh = cv2.bitwise_not(query)
37+
#thresh[thresh > 0] = 255
38+
39+
# initialize the outline image, find the outermost
40+
# contours (the outline) of the pokemone, then draw
41+
# it
42+
#outline = np.zeros(query.shape, dtype = "uint8")
43+
#(cnts, _) = cv2.findContours(thresh.copy(), cv2.RETR_EXTERNAL,
44+
# cv2.CHAIN_APPROX_SIMPLE)
45+
#cnts = sorted(cnts, key = cv2.contourArea, reverse = True)[0]
46+
#cv2.drawContours(outline, [cnts], -1, 255, -1)
47+
48+
features = cd.describe_hog(query)
49+
50+
# perform the search
51+
searcher = Searcher(args["index"])
52+
results = searcher.search(features)
53+
54+
# display the query
55+
cv2.imshow("Query", query)
56+
print ("Reached here")
57+
58+
# loop over the results
59+
for (score, resultID) in results:
60+
# load the result image and display it
61+
print (score)
62+
result = cv2.imread(args["result_path"] + "/" + resultID)
63+
cv2.imshow("Result", result)
64+
cv2.waitKey(0)

0 commit comments

Comments
 (0)