def getXOR(out): imgFinal, contourFinal, _ = cv.findContours(out, cv.RETR_TREE, cv.CHAIN_APPROX_SIMPLE) imgFinal = prep.removeHoles(imgFinal) largestFinalContour = util.findLargestContour(contourFinal) maskHeight, maskWidth = out.shape mask = np.zeros((maskHeight, maskWidth, 3), np.uint8) mask = cv.cvtColor(mask, cv.COLOR_BGR2GRAY) mask = cv.drawContours(mask, [largestFinalContour], -1, (255), 1) mask = np.dstack((mask, mask, mask)) cv.fillPoly(mask, pts=[largestFinalContour], color=(255, 255, 255)) # Fill with circle maskCenter = tuple(np.array(mask.shape[1::-1]) / 2) rotationMatrix = cv.getRotationMatrix2D(maskCenter, 180, 1.0) maskRotated = cv.warpAffine(mask, rotationMatrix, mask.shape[1::-1], flags=cv.INTER_LINEAR) maskXORed = cv.bitwise_xor(mask, maskRotated) deviation = (np.count_nonzero(maskXORed) / np.count_nonzero(mask)) * 100 return deviation
def getArrayOfRadiusMelanoma(contour): contourTemp = util.findLargestContour(contour) # Find largest contour x, y = getCenterOfCircle(contourTemp) # Get center of circle arrOfRadius = [] for i in range(0, len(contourTemp)): arrOfRadius.append( np.sqrt( np.power(contourTemp[i][0][0] - x, 2) + np.power(contourTemp[i][0][1] - y, 2))) return arrOfRadius
def getMelanomaWithoutCircle(out, contours): blankImageHeight, blankImageWidth = out.shape blankImage = np.zeros((blankImageHeight, blankImageWidth, 3), np.uint8) # Create a circle contour contourNew = util.findLargestContour(contours) # x, y, radius = getEquivalentCircle(contourNew) ellipse = getFittedEllipse(contourNew) # cv.circle(img, (x, y), int(radius), (0, 255, 0), 2) # cv.circle(blankImage, (x, y), int(radius), (255, 255, 255), 2) cv.ellipse(blankImage, ellipse, (255, 255, 255), 2) blankImageBW = cv.cvtColor(blankImage, cv.COLOR_BGR2GRAY) imgBlankImage, contourBlankImage, _ = cv.findContours( blankImageBW, cv.RETR_TREE, cv.CHAIN_APPROX_SIMPLE) _, imgBlankImage = prep.fillEmpty(contourBlankImage, imgBlankImage) # Prepare melanoma contour imgFinal, contourFinal, _ = cv.findContours(out, cv.RETR_TREE, cv.CHAIN_APPROX_SIMPLE) imgFinal = prep.removeHoles(imgFinal) largestFinalContour = util.findLargestContour(contourFinal) # Insert circle into melanoma finalBlankImageHeight, finalBlankImageWidth = imgFinal.shape # Make a new blank image finalBlankImage = np.zeros((blankImageHeight, blankImageWidth, 3), np.uint8) finalBlankImage = cv.cvtColor(finalBlankImage, cv.COLOR_BGR2GRAY) finalBlankImage = cv.drawContours(finalBlankImage, [largestFinalContour], 0, 255) # Draw melanoma contour finalBlankImage, finalBlankContour, _ = cv.findContours( finalBlankImage, cv.RETR_TREE, cv.CHAIN_APPROX_SIMPLE) # Find contour finalBlankImage = prep.removeHoles(finalBlankImage) # Fill contour cv.fillPoly(finalBlankImage, pts=[util.findLargestContour(contourBlankImage)], color=(0, 0, 0)) # Fill with circle return (finalBlankImage, contourBlankImage)
def getColorDeviation(img, out): img = cv.cvtColor(img, cv.COLOR_BGR2HSV) imgFinal, contourFinal, _ = cv.findContours(out, cv.RETR_TREE, cv.CHAIN_APPROX_SIMPLE) imgFinal = prep.removeHoles(imgFinal) _, contourFinal, _ = cv.findContours(imgFinal, cv.RETR_TREE, cv.CHAIN_APPROX_SIMPLE) largestFinalContour = util.findLargestContour(contourFinal) maskHeight, maskWidth = out.shape mask = np.zeros((maskHeight, maskWidth, 3), np.uint8) mask = cv.cvtColor(mask, cv.COLOR_BGR2GRAY) mask = cv.drawContours(mask, [largestFinalContour], -1, (255), 1) mask = np.dstack((mask, mask, mask)) cv.fillPoly(mask, pts = [largestFinalContour], color = (1, 1, 1)) # Fill with circle kernel = cv.getStructuringElement(cv.MORPH_ELLIPSE, (25,25)) mask = cv.erode(mask, kernel, iterations = 1) tempImg = img * mask tempImgArr = tempImg[ (tempImg[:,:,1] != 0) | (tempImg[:,:,0] != 0) | (tempImg[:,:,2] != 0)] stddevs = np.std(tempImgArr, axis=0) means = np.mean(tempImgArr, axis=0) return (stddevs, means, tempImg)
def getNewXOR(img): thresh, contours = util.getContourHSV(img) largestContour = util.findLargestContour(contours) maskHeight, maskWidth, _ = img.shape mask = np.zeros((maskHeight, maskWidth, 3), np.uint8) mask = cv.cvtColor(mask, cv.COLOR_BGR2GRAY) mask = cv.drawContours(mask, [largestContour], -1, (255), 1) mask = np.dstack((mask, mask, mask)) cv.fillPoly(mask, pts=[largestContour], color=(255, 255, 255)) # Fill with circle maskCenter = tuple(np.array(mask.shape[1::-1]) / 2) rotationMatrix = cv.getRotationMatrix2D(maskCenter, 180, 1.0) maskRotated = cv.warpAffine(mask, rotationMatrix, mask.shape[1::-1], flags=cv.INTER_LINEAR) maskXORed = cv.bitwise_xor(mask, maskRotated) devitaion = (np.count_nonzero(maskXORed) / np.count_nonzero(mask)) * 100 return devitaion
def analyze(paramArr): # Read image path, filename and output file from params imagePath, fileName, outputFile = paramArr #print(imagePath) proportions = 0 # Read the image first img = cv.imread(imagePath) # Reading image hsvimg = cv.cvtColor(img, cv.COLOR_BGR2HSV) _, contours = util.getContourContrast( img) # Method for getting threshold and contours contour = util.findLargestContour(contours) threshShapeHeight, threshSHapeWidth, _ = img.shape thresh = np.zeros((threshShapeHeight, threshSHapeWidth, 1), dtype=np.uint8) thresh = cv.drawContours(thresh, [contour], 0, 255) ([contour], thresh) = prep.fillEmpty([contour], thresh) # ================ # Get rid of holestours # # There are some holes in the contour so this gets rid of them # ================ closing = prep.removeHoles(thresh) # ===================== # Get rid of noise dots # # This gets rid of noise dots that are around the contour # ===================== out = prep.removeNoise(closing) # ================= # B Rule # # Border rule implementation # ================= finalBlankImage, contourBlankImage = border.getMelanomaWithoutCircle( out, thresh, contours) # for cont in contourBlankImage: # print(len(cont)) # cv.imshow('Final blank image', finalBlankImage) # cv.waitKey() # cv.destroyAllWindows() # exit() sCnt = border.getMelanomaWithoutCircleSurface(finalBlankImage, contourBlankImage) borderDeviation = (sCnt * 2) / cv.contourArea( util.findLargestContour(contourBlankImage)) # ============= # D Rule # # If diameter of lesion is bigger than 6mm # ============= calculatedDiameter = diameter.getMinEnclosingCircleRadius( util.findLargestContour(contours)) * 2 # realDiameter = diameter / proportions realDiameter = 0 # ============= # C Rule # # Color detecion # ============= # Prepare melanoma contour stddevs, means = color.getColorDeviation(img, out) hstddevs, sstddevs, vstddevs = stddevs hmeans, smeans, vmeans = means # ============= # A Rule # # Asymmetry rule # ============= asymmetryResult = min([ res for _, res in asymmetry.getAsymmetryRotationResults(thresh).items() ]) # asymmetryResult = asymmetry.getAsymmetryRotationResults(thresh) # meanAsymmetryResult = mean([res for _, res in asymmetryResult.items()]) * 100 # asymmetryDeviation = asymmetry.getNewXOR(img) csvLine = str(fileName) + ',' + str(asymmetryResult) + ',' + str( borderDeviation) + ',' + str(hstddevs) + ',' + str(hmeans) + ',' + str( sstddevs) + ',' + str(smeans) + ',' + str(vstddevs) + ',' + str( vmeans) + ',' + str(realDiameter) + '\n' file = open(outputFile, 'a') file.write(csvLine) file.close()