diff --git a/__pycache__/detect.cpython-38.pyc b/__pycache__/detect.cpython-38.pyc index 3370682..74d3b26 100644 Binary files a/__pycache__/detect.cpython-38.pyc and b/__pycache__/detect.cpython-38.pyc differ diff --git a/detect.cpython-38-x86_64-linux-gnu.so b/detect.cpython-38-x86_64-linux-gnu.so deleted file mode 100755 index 5e1161d..0000000 Binary files a/detect.cpython-38-x86_64-linux-gnu.so and /dev/null differ diff --git a/detect.py b/detect.py index 78aef57..ff9e8fd 100644 --- a/detect.py +++ b/detect.py @@ -76,13 +76,13 @@ ap.add_argument("-n", "--number", type=int, required=False, args = vars(ap.parse_args()) args2 = ap.parse_args()""" def detect(calibration_width, img_file, show, quick): - selected = 2 + list = [] #if type(args["number"]) == type(selected): # selected = args["number"] # load the image, convert it to grayscale, and blur it slightly image = None - print(str(type(img_file))) + #print(str(type(img_file))) if str(type(img_file)) == "": image = img_file.copy() else: @@ -91,7 +91,7 @@ def detect(calibration_width, img_file, show, quick): #image = img_file.copy() #image = cv2.resize(image, (int(image.shape[1]*1), int(image.shape[0]*1))) image = cv2.resize(image, (1000, int( - image.shape[0]/image.shape[1] * 1000)), interpolation=cv2.INTER_NEAREST) + image.shape[0]/image.shape[1] * 1000)), interpolation=cv2.INTER_NEAREST) if show and not quick: cv2.namedWindow("Item Sorter") @@ -232,139 +232,134 @@ def detect(calibration_width, img_file, show, quick): dimA = dA / pixelsPerMetric dimB = dB / pixelsPerMetric - if num == num or show: - area_box = dA * dB - (x, y), radius = cv2.minEnclosingCircle(c) - area_contour = cv2.contourArea(c) - area_circle = math.pi * pow(radius, 2) - boxiness = area_contour / area_box - circleness = area_contour / area_circle - circular = False - rectangular = False - if boxiness > circleness: - rectangular = True - #cv2.drawContours(orig, [box.astype("int")], -1, (0, 255, 0), 2) - else: - circular = True - cv2.circle(orig, (int(x), int(y)), int(radius), (255, 0, 0), 2) - - objtype = "Unknown" - itemw = larger(dimA, dimB) - itemwr = itemw - itemwr *= 8 - itemwr = round(itemwr) - itemwr /= 8 - - itemh = smaller(dimA, dimB) - itemhr = itemh - itemhr *= 16 - itemhr = round(itemhr) - itemhr /= 16 - if circular and itemwr == 0.75: - objtype = "Penny" - iteml = 0 + # Item detection + area_box = dA * dB + (x, y), radius = cv2.minEnclosingCircle(c) + area_contour = cv2.contourArea(c) + area_circle = math.pi * pow(radius, 2) + boxiness = area_contour / area_box + circleness = area_contour / area_circle + circular = False + rectangular = False + if boxiness > circleness: + rectangular = True + #cv2.drawContours(orig, [box.astype("int")], -1, (0, 255, 0), 2) + else: + circular = True + cv2.circle(orig, (int(x), int(y)), int(radius), (255, 0, 0), 2) + objtype = "Unknown" + itemw = larger(dimA, dimB) + itemwr = itemw + itemwr *= 8 + itemwr = round(itemwr) + itemwr /= 8 + itemh = smaller(dimA, dimB) + itemhr = itemh + itemhr *= 16 + itemhr = round(itemhr) + itemhr /= 16 + if circular and itemwr == 0.75: + objtype = "Penny" + iteml = 0 + else: + if circular and near(radius * 2 / pixelsPerMetric, 0.38, 0.03): + # Keps nut or spacer + objtype = "Spacer" + mask = np.zeros(gray.shape, np.uint8) + cv2.drawContours(mask, [c], 0, 255, -1) + #pixelpoints = np.transpose(np.nonzero(mask)) + hsv = cv2.cvtColor(orig, cv2.COLOR_BGR2HSV) + mean_val = cv2.mean(hsv, mask=mask) + #print(str(mean_val[0])) + if near(mean_val[0], 47, 5) and near(mean_val[1], 70, 5) and near(mean_val[2], 78, 5): + objtype = "Keps Nut" + if circular and near(radius / pixelsPerMetric, 0.23, 0.02): + objtype = "Washer" + epsilon = 3 # 0.02*cv2.arcLength(c,True) + # print(str(epsilon)) + approx = cv2.approxPolyDP(c, epsilon, True) + hull = cv2.convexHull(approx, returnPoints=False) + hull2 = cv2.convexHull(c) + defects = cv2.convexityDefects(c, hull) + #print(str(defects.size) + " match") + cv2.drawContours(orig, (hull2), -1, (0, 0, 255), 3) + cv2.drawContours(orig, (approx), -1, (255, 0, 0), 3) + convexness = area_contour / cv2.contourArea(hull2) + #print(str(convexness) + " % fill") + # if not cv2.isContourConvex(approx): + # if cv2.matchShapes(hull, c, 1, 0.0) > 1: + if defects is not None and defects.size > 5 and (convexness < 0.9 or boxiness < 0.75) and rectangular: + objtype = "Screw" + iteml = larger(dimA, dimB) + #print("Screw Length (RAW): " + str(iteml)) + iteml = sizeVexScrew(radius * 2 / pixelsPerMetric) + #print("Rounded Length: " + str(iteml)) else: - if circular and near(radius * 2 / pixelsPerMetric, 0.38, 0.03): - # Keps nut or spacer - objtype = "Spacer" - mask = np.zeros(gray.shape, np.uint8) - cv2.drawContours(mask, [c], 0, 255, -1) - #pixelpoints = np.transpose(np.nonzero(mask)) - hsv = cv2.cvtColor(orig, cv2.COLOR_BGR2HSV) - mean_val = cv2.mean(hsv, mask=mask) - #print(str(mean_val[0])) - if near(mean_val[0], 47, 5) and near(mean_val[1], 70, 5) and near(mean_val[2], 78, 5): - objtype = "Keps Nut" - if circular and near(radius / pixelsPerMetric, 0.23, 0.02): - objtype = "Washer" - epsilon = 3 # 0.02*cv2.arcLength(c,True) - # print(str(epsilon)) - approx = cv2.approxPolyDP(c, epsilon, True) - hull = cv2.convexHull(approx, returnPoints=False) - hull2 = cv2.convexHull(c) - defects = cv2.convexityDefects(c, hull) - #print(str(defects.size) + " match") - cv2.drawContours(orig, (hull2), -1, (0, 0, 255), 3) - cv2.drawContours(orig, (approx), -1, (255, 0, 0), 3) - convexness = area_contour / cv2.contourArea(hull2) - #print(str(convexness) + " % fill") - # if not cv2.isContourConvex(approx): - # if cv2.matchShapes(hull, c, 1, 0.0) > 1: - if defects is not None and defects.size > 5 and (convexness < 0.9 or boxiness < 0.75) and rectangular: - objtype = "Screw" - iteml = larger(dimA, dimB) - #print("Screw Length (RAW): " + str(iteml)) - iteml = sizeVexScrew(radius * 2 / pixelsPerMetric) - #print("Rounded Length: " + str(iteml)) - else: - if itemhr == 0.3125 and rectangular: - objtype = "Standoff" - iteml = sizeStandoff(itemw) - - if itemhr == 0.1875 and rectangular: - objtype = "Axle" - iteml = (radius * 2 / pixelsPerMetric + itemw) / 2 - - rows, cols = orig.shape[:2] - [vx, vy, xx, yy] = cv2.fitLine(c, cv2.DIST_L2, 0, 0.01, 0.01) - lefty = int((-xx*vy/vx) + yy) - righty = int(((cols-xx)*vy/vx)+yy) - # cv2.line(orig,(cols-1,righty),(0,lefty),(0,255,0),2) - slope = (lefty - righty) / (1 - cols) - angle = math.atan(slope) - xpos = x - math.cos(angle) * radius - ypos = y - math.sin(angle) * radius - xpos2 = x + math.cos(angle) * radius - ypos2 = y + math.sin(angle) * radius - if xpos > xpos2: - swap(xpos, xpos2) - swap(ypos, ypos2) - if rectangular: - cv2.line(orig, (int(xpos), int(ypos)), - (int(xpos2), int(ypos2)), (255, 127, 0), 2) - # print(str(iteml)) - # draw the object sizes on the image - if show or True: - # cv2.putText(orig, "{:.5f}in".format(itemhr), - # (int(trbrX + 20), int(trbrY)), cv2.FONT_HERSHEY_SIMPLEX, - # 0.65, (255, 255, 255), 2) - if circular: - cv2.putText(orig, str(objtype), - (int(x - 25), int(y + radius + 20) - ), cv2.FONT_HERSHEY_SIMPLEX, - 0.6, (50, 50, 220), 2) - else: - cv2.putText(orig, str(objtype), - (int(xpos2 + 10), int(ypos2 + 20) - ), cv2.FONT_HERSHEY_SIMPLEX, - 0.6, (50, 50, 220), 2) - output = "" - objname = objtype; - if objtype == "Unknown": - output = "{:.2f}in".format(itemw) + " x {:.2f}in".format(itemh) - if objtype == "Screw" or objtype == "Standoff": - output = str(iteml) + "in" - objname += str(iteml) - if objtype == "Axle": - output = "{:.2f}in".format(iteml) - objname += str(itemwr) - print(objname) - if circular: - cv2.putText(orig, output, # print data - (int(x - 25), int(y + radius + 40) - ), cv2.FONT_HERSHEY_SIMPLEX, - 0.5, (50, 50, 220), 1) - else: - cv2.putText(orig, output, # print data - (int(xpos2 + 10), int(ypos2 + 40) - ), cv2.FONT_HERSHEY_SIMPLEX, - 0.5, (50, 50, 220), 1) - - # show the output image - if show: - cv2.imshow("Item Sorter", orig) - #cv2.waitKey(1) + if itemhr == 0.3125 and rectangular: + objtype = "Standoff" + iteml = sizeStandoff(itemw) + if itemhr == 0.1875 and rectangular: + objtype = "Axle" + iteml = (radius * 2 / pixelsPerMetric + itemw) / 2 + rows, cols = orig.shape[:2] + [vx, vy, xx, yy] = cv2.fitLine(c, cv2.DIST_L2, 0, 0.01, 0.01) + lefty = int((-xx*vy/vx) + yy) + righty = int(((cols-xx)*vy/vx)+yy) + # cv2.line(orig,(cols-1,righty),(0,lefty),(0,255,0),2) + slope = (lefty - righty) / (1 - cols) + angle = math.atan(slope) + xpos = x - math.cos(angle) * radius + ypos = y - math.sin(angle) * radius + xpos2 = x + math.cos(angle) * radius + ypos2 = y + math.sin(angle) * radius + if xpos > xpos2: + swap(xpos, xpos2) + swap(ypos, ypos2) + if rectangular: + cv2.line(orig, (int(xpos), int(ypos)), + (int(xpos2), int(ypos2)), (255, 127, 0), 2) + # print(str(iteml)) + # draw the object sizes on the image + # cv2.putText(orig, "{:.5f}in".format(itemhr), + # (int(trbrX + 20), int(trbrY)), cv2.FONT_HERSHEY_SIMPLEX, + # 0.65, (255, 255, 255), 2) + if circular: + cv2.putText(orig, str(objtype), + (int(x - 25), int(y + radius + 20) + ), cv2.FONT_HERSHEY_SIMPLEX, + 0.6, (50, 50, 220), 2) + else: + cv2.putText(orig, str(objtype), + (int(xpos2 + 10), int(ypos2 + 20) + ), cv2.FONT_HERSHEY_SIMPLEX, + 0.6, (50, 50, 220), 2) + output = "" + objname = objtype; + if objtype == "Unknown": + output = "{:.2f}in".format(itemw) + " x {:.2f}in".format(itemh) + if objtype == "Screw" or objtype == "Standoff": + output = str(iteml) + "in" + objname += str(iteml) + if objtype == "Axle": + output = "{:.2f}in".format(iteml) + objname += str(itemwr) + #print(objname) + list.append(objname) + if circular: + cv2.putText(orig, output, # print data + (int(x - 25), int(y + radius + 40) + ), cv2.FONT_HERSHEY_SIMPLEX, + 0.5, (50, 50, 220), 1) + else: + cv2.putText(orig, output, # print data + (int(xpos2 + 10), int(ypos2 + 40) + ), cv2.FONT_HERSHEY_SIMPLEX, + 0.5, (50, 50, 220), 1) + # show the output image + if show and not quick: + cv2.imshow("Item Sorter", orig) + #cv2.waitKey(1) if quick: - return orig + return (list, orig) else: cv2.waitKey(0) diff --git a/run_detect.py b/run_detect.py index 9f412d9..637d1ed 100644 --- a/run_detect.py +++ b/run_detect.py @@ -5,14 +5,28 @@ from imutils.video import FPS calibration_width = 0.75 image = "img7.jpg" images = ("img.jpg", "img2.jpg", "img3.jpg", "img4.jpg", "img5.jpg", "img6.jpg", "img7.jpg", "img8.jpg") +#images = ("img.jpg", "img2.jpg") video = False def go(): for file in images: - detect.detect(calibration_width, file, True, False) + items,output = detect.detect(calibration_width, file, True, True) + print(str(items)) + if "Penny" in items: + items.remove("Penny") + itema = items[0] + valid = True + for item in items: + if item != itema: + print("Too many items!") + valid = False + break + if valid: + print("Found " + itema) if not video: elapsed_time = timeit.timeit(go, number=1)/1 print(elapsed_time) + else : #tcp capture = cv2.VideoCapture('udpsrc port=5001 ! gdpdepay ! rtph264depay ! avdec_h264 ! videoconvert ! videorate ! video/x-raw,framerate=5/1 ! appsink', cv2.CAP_GSTREAMER) capture = cv2.VideoCapture('udpsrc port=9000 caps="application/x-rtp, media=(string)video, clock-rate=(int)90000, encoding-name=(string)H264" ! rtph264depay ! avdec_h264 ! videoconvert ! appsink sync=false', cv2.CAP_GSTREAMER) @@ -32,7 +46,8 @@ else : #print('frame') if x > 1: ret,frame = capture.retrieve() - cv2.imshow('Item Sorter', detect.detect(calibration_width, frame, True, True)) + list,output = detect.detect(calibration_width, frame, True, True) + cv2.imshow('Item Sorter', output) x = 0 if cv2.waitKey(1)&0xFF == ord('q'): break