|
|
|
|
|
import cv2 |
|
|
|
|
|
import sched, time |
|
|
import math |
|
|
import fitz |
|
|
import pandas as pd |
|
|
import random |
|
|
|
|
|
|
|
|
|
|
|
from PIL import Image , ImageDraw, ImageFont , ImageColor |
|
|
import numpy as np |
|
|
import gradio as gr |
|
|
|
|
|
import os |
|
|
from db import dropbox_upload_file |
|
|
from pathlib import Path |
|
|
from PreprocessingFoundation import rmv_text,rmv_dashedLines |
|
|
|
|
|
from googleapiclient.discovery import build |
|
|
from google.oauth2 import service_account |
|
|
import pygsheets |
|
|
|
|
|
|
|
|
'''push output to dropbox''' |
|
|
|
|
|
|
|
|
|
|
|
def pushToDropbox(plan1,area,df): |
|
|
plan=Path(os.path.split(plan1)[1]).stem |
|
|
|
|
|
a=dropbox_upload_file('.',local_file=area,dropbox_file_path='/savedMeasurements/'+plan+'area.png') |
|
|
|
|
|
d=dropbox_upload_file('.',local_file=df,dropbox_file_path='/savedMeasurements/'+plan+'summary.csv') |
|
|
|
|
|
def exportToExcel(plan,Dictionary): |
|
|
|
|
|
d=dropbox_upload_file('.',local_file=Dictionary,dropbox_file_path='/savedMeasurements/'+plan+'summary.csv') |
|
|
|
|
|
def auth(username,password): |
|
|
if username=="alaa" and password=="1234": |
|
|
return True |
|
|
|
|
|
def plan2img(plan): |
|
|
if 'foundation' in plan.lower(): |
|
|
noTextImg=rmv_text(plan) |
|
|
clean_img=rmv_dashedLines(noTextImg) |
|
|
return clean_img |
|
|
|
|
|
else: |
|
|
|
|
|
|
|
|
doc = fitz.open(plan) |
|
|
for page in doc: |
|
|
pix = page.get_pixmap(dpi=200) |
|
|
pl=Image.frombytes('RGB', [pix.width,pix.height],pix.samples) |
|
|
pl1=np.array(pl) |
|
|
|
|
|
return pl1 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def detectCircles(imgOriginal ): |
|
|
im=imgOriginal.copy() |
|
|
imgGry1 = cv2.cvtColor(im, cv2.COLOR_BGR2GRAY) |
|
|
kernel=np.ones((3,3),np.uint8) |
|
|
er1=cv2.erode(imgGry1,kernel, iterations=2) |
|
|
|
|
|
er1=cv2.dilate(er1,kernel, iterations=1) |
|
|
gray_blurred = cv2.blur(er1, (3,3 )) |
|
|
|
|
|
|
|
|
detected_circles = cv2.HoughCircles( gray_blurred, cv2.HOUGH_GRADIENT, 1, 50, param1= 550, |
|
|
param2 =21, minRadius = 20, maxRadius = 40) |
|
|
|
|
|
|
|
|
if detected_circles is not None: |
|
|
|
|
|
detected_circles = np.uint16(np.around(detected_circles)) |
|
|
detected_circles = np.round(detected_circles[0, :]).astype("int") |
|
|
|
|
|
for (x, y, r) in detected_circles: |
|
|
cv2.circle(im, (x, y), r, (255, 255, 255), 5) |
|
|
im=cv2.medianBlur(im,1) |
|
|
print('circles') |
|
|
|
|
|
return im |
|
|
|
|
|
def detectSmallCircles(img ): |
|
|
|
|
|
im=img.copy() |
|
|
imgGry1 = cv2.cvtColor(im, cv2.COLOR_BGR2GRAY) |
|
|
kernel=np.ones((3,3),np.uint8) |
|
|
er1=cv2.erode(imgGry1,kernel, iterations=1) |
|
|
|
|
|
|
|
|
detected_circles = cv2.HoughCircles( imgGry1, cv2.HOUGH_GRADIENT, 1, 60, param1 =550, |
|
|
param2 =13, minRadius = 1, maxRadius = 10) |
|
|
|
|
|
|
|
|
if detected_circles is not None: |
|
|
|
|
|
detected_circles = np.uint16(np.around(detected_circles)) |
|
|
detected_circles = np.round(detected_circles[0, :]).astype("int") |
|
|
|
|
|
for (x, y, r) in detected_circles: |
|
|
cv2.circle(im, (x, y), r+1, (255, 255, 255), -1) |
|
|
|
|
|
return im |
|
|
|
|
|
|
|
|
def DashedPreprocessing(imgOriginal,imgnoSmall): |
|
|
h,w=imgOriginal.shape[0:2] |
|
|
|
|
|
imgBW=cv2.threshold(imgnoSmall, 180, 255, cv2.THRESH_BINARY)[1] |
|
|
|
|
|
im_copy=imgBW.copy() |
|
|
im_copy1=im_copy |
|
|
kernel1 = np.ones((3,5),np.uint8) |
|
|
kernel2 = np.ones((9,9),np.uint8) |
|
|
kernel3= np.ones((3,3),np.uint8) |
|
|
imgGray=cv2.cvtColor(imgBW,cv2.COLOR_BGR2GRAY) |
|
|
imgBW1=cv2.threshold(imgGray, 200, 255, cv2.THRESH_BINARY_INV)[1] |
|
|
|
|
|
img1=cv2.erode(imgBW1, kernel1, iterations=1) |
|
|
img2=cv2.dilate(img1, kernel2, iterations=3) |
|
|
img3 = cv2.bitwise_and(imgBW1,img2) |
|
|
img3= cv2.bitwise_not(img3) |
|
|
img4 = cv2.bitwise_and(imgBW1,imgBW1,mask=img3) |
|
|
img4=cv2.blur(img4,(7,7)) |
|
|
if h > w : |
|
|
max = h |
|
|
min = w |
|
|
else: |
|
|
max = w |
|
|
min = h |
|
|
return img4, imgBW, max,min |
|
|
|
|
|
def removeDashedLines(img4, imgBW ,max,min): |
|
|
|
|
|
imgLines= cv2.HoughLinesP(img4,1,np.pi/310,30,minLineLength=(max-min)//1.8,maxLineGap = 120) |
|
|
|
|
|
|
|
|
for i in range(len(imgLines)): |
|
|
for x1,y1,x2,y2 in imgLines[i]: |
|
|
cv2.line(imgBW,(x1,y1),(x2,y2),(0,255,0),2) |
|
|
|
|
|
im_copy=imgBW.copy() |
|
|
green=im_copy[:,:,1] |
|
|
|
|
|
return green |
|
|
|
|
|
def removeSmallDashes(imgOriginal,green): |
|
|
smalldashes=green.copy() |
|
|
smalldashes=cv2.bitwise_not(smalldashes) |
|
|
|
|
|
kernel3= np.ones((3,3),np.uint8) |
|
|
|
|
|
img1=cv2.dilate(smalldashes, kernel3, iterations=2) |
|
|
img2=cv2.erode(img1, kernel3, iterations=2) |
|
|
|
|
|
smalldashes=cv2.medianBlur(img2,5) |
|
|
smalldashes=cv2.medianBlur(smalldashes,7) |
|
|
|
|
|
smalldashesOut=green.copy() |
|
|
smalldashesOut=cv2.cvtColor(smalldashesOut,cv2.COLOR_GRAY2BGR) |
|
|
imgLines= cv2.HoughLinesP(smalldashes,1,np.pi/150,27,minLineLength=10,maxLineGap = 70) |
|
|
|
|
|
imgCopy=imgOriginal.copy() |
|
|
for i in range(len(imgLines)): |
|
|
for x1,y1,x2,y2 in imgLines[i]: |
|
|
cv2.line(smalldashesOut,(x1,y1),(x2,y2),(0,255,0),2) |
|
|
|
|
|
|
|
|
smalldashesOut=smalldashesOut[:,:,1] |
|
|
|
|
|
for i in range(len(imgLines)): |
|
|
for x1,y1,x2,y2 in imgLines[i]: |
|
|
cv2.line(imgCopy,(x1,y1),(x2,y2),(0,255,0),6) |
|
|
|
|
|
imgCopy=imgCopy[:,:,1] |
|
|
|
|
|
return imgCopy,smalldashesOut |
|
|
|
|
|
def euclidian_distance(point1, point2): |
|
|
return sum([(point1[x] - point2[x]) ** 2 for x in range(len(point1))]) ** 0.5 |
|
|
|
|
|
def removeDashedLinesSmall(img4, imgBW ,max,min): |
|
|
|
|
|
imgBW=cv2.cvtColor(imgBW,cv2.COLOR_GRAY2BGR) |
|
|
|
|
|
imgLines= cv2.HoughLinesP(img4,1,np.pi/100,20,minLineLength=(max-min)//2.2,maxLineGap = 70) |
|
|
|
|
|
for i in range(len(imgLines)): |
|
|
for x1,y1,x2,y2 in imgLines[i]: |
|
|
dist=euclidian_distance((x1,y1), (x2,y2)) |
|
|
|
|
|
if dist >= (max-min)//2.1 and dist < (max-min)//1.9: |
|
|
cv2.line(imgBW,(x1,y1),(x2,y2),(0,255,0),3) |
|
|
|
|
|
im_copy=imgBW.copy() |
|
|
green=im_copy[:,:,1] |
|
|
|
|
|
return green |
|
|
|
|
|
def ConnectBeamLines(smalldashesOut): |
|
|
green1=cv2.bitwise_not(smalldashesOut) |
|
|
green2=smalldashesOut.copy() |
|
|
green2=cv2.cvtColor(green2,cv2.COLOR_GRAY2BGR) |
|
|
imgLines= cv2.HoughLinesP(green1,0.05,np.pi/250,10,minLineLength=25,maxLineGap = 20) |
|
|
for i in range(len(imgLines)): |
|
|
for x1,y1,x2,y2 in imgLines[i]: |
|
|
cv2.line(green2,(x1,y1),(x2,y2),(0,0,0),1) |
|
|
|
|
|
imgLines= cv2.HoughLinesP(green1,0.3,np.pi/360,10,minLineLength=25,maxLineGap = 20) |
|
|
|
|
|
|
|
|
for i in range(len(imgLines)): |
|
|
for x1,y1,x2,y2 in imgLines[i]: |
|
|
cv2.line(green2,(x1,y1),(x2,y2),(0,0,0),1) |
|
|
|
|
|
return green2 |
|
|
|
|
|
def allpreSteps(imgOriginal): |
|
|
noCircles=detectCircles(imgOriginal) |
|
|
imgnoSmall=detectSmallCircles(noCircles ) |
|
|
img4,imgBW,max,min=DashedPreprocessing(imgOriginal,imgnoSmall) |
|
|
green=removeDashedLines(img4,imgBW,max,min) |
|
|
imgCopy,smalldashesOut=removeSmallDashes(imgOriginal,green) |
|
|
noSmallDashes=removeDashedLinesSmall(img4, smalldashesOut ,max,min) |
|
|
green2=ConnectBeamLines(noSmallDashes) |
|
|
|
|
|
return green2 |
|
|
|
|
|
def ChangeBrightness(img,k): |
|
|
imgdarker = 255 * (img/255)**k |
|
|
|
|
|
imgdarker = imgdarker.astype('uint8') |
|
|
return imgdarker |
|
|
|
|
|
def preprocessold(img,number): |
|
|
|
|
|
|
|
|
blurG = cv2.GaussianBlur(ChangeBrightness(img,6),(3,3),0) |
|
|
|
|
|
imgGry = cv2.cvtColor(blurG, cv2.COLOR_BGR2GRAY) |
|
|
|
|
|
kernel=np.ones((3,3),np.uint8) |
|
|
|
|
|
er1=cv2.dilate(imgGry,kernel, iterations=2) |
|
|
|
|
|
er2=cv2.erode(er1,kernel, iterations=3) |
|
|
er3=cv2.dilate(er2,kernel, iterations=4) |
|
|
|
|
|
if number == 0: |
|
|
ret3, thresh = cv2.threshold(er3, 200, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU) |
|
|
else: |
|
|
ret3, thresh = cv2.threshold(er3, 220, 255, cv2.THRESH_BINARY_INV) |
|
|
|
|
|
return thresh |
|
|
|
|
|
|
|
|
def preprocess(imgOriginal,number,green2): |
|
|
|
|
|
img1=preprocessold(imgOriginal,number) |
|
|
imgGry0 = cv2.cvtColor(imgOriginal , cv2.COLOR_BGR2GRAY) |
|
|
|
|
|
kernel=np.ones((3,3),np.uint8) |
|
|
|
|
|
anding=cv2.bitwise_and(green2,green2,mask=img1) |
|
|
anding = cv2.cvtColor(anding , cv2.COLOR_BGR2GRAY) |
|
|
|
|
|
return anding |
|
|
|
|
|
"""# ROI (levels) |
|
|
|
|
|
## Detect regions with specific color and mask them |
|
|
""" |
|
|
|
|
|
def hexRGB(color): |
|
|
color=color.lstrip('#') |
|
|
color= tuple(int(color[i:i+2], 16) for i in (0, 2, 4)) |
|
|
color=np.array(color) |
|
|
return color |
|
|
def DetectColor(img,color=0): |
|
|
|
|
|
imgCopy=img.copy() |
|
|
imgCopy=cv2.cvtColor(imgCopy,cv2.COLOR_BGR2HSV) |
|
|
tol=5 |
|
|
color=hexRGB(color) |
|
|
h,s,v = cv2.cvtColor(np.uint8([[[color[2],color[1],color[0]]]]),cv2.COLOR_BGR2HSV)[0][0] |
|
|
|
|
|
lower =np.array( [h- tol, 100, 100 ], dtype='uint8') |
|
|
upper = np.array( [h + tol, 255, 255],dtype='uint8') |
|
|
|
|
|
mask = cv2.inRange(imgCopy, lower , upper) |
|
|
|
|
|
detectedColors = cv2.bitwise_and(imgCopy,imgCopy, mask= mask) |
|
|
|
|
|
kernel=np.ones((3,3),np.uint8) |
|
|
mask=cv2.dilate(mask,kernel, iterations=5) |
|
|
mask=cv2.erode(mask,kernel, iterations=4) |
|
|
|
|
|
detectedColors=cv2.dilate(detectedColors,kernel, iterations=5) |
|
|
detectedColors=cv2.erode(detectedColors,kernel, iterations=4) |
|
|
|
|
|
detectedColors=cv2.cvtColor(detectedColors,cv2.COLOR_HSV2BGR) |
|
|
detectedColors=cv2.medianBlur(detectedColors,7) |
|
|
|
|
|
|
|
|
return mask, detectedColors, color |
|
|
|
|
|
|
|
|
def detectAllColors(img,finalColorArray): |
|
|
for i in range(len(finalColorArray)): |
|
|
detectedColors= DetectColor(img,finalColorArray[i])[1] |
|
|
if i == 0: |
|
|
allcolorsImg=cv2.bitwise_or(detectedColors,detectedColors) |
|
|
else: |
|
|
allcolorsImg=cv2.bitwise_or(allcolorsImg,detectedColors) |
|
|
allcolorsImg= cv2.medianBlur(allcolorsImg,7) |
|
|
|
|
|
return allcolorsImg |
|
|
|
|
|
def colorOrder(img,finalColorArray): |
|
|
newimg=img.copy() |
|
|
arraycolor=[] |
|
|
allcolorsImg= detectAllColors(img,finalColorArray) |
|
|
allcolorsImgG= cv2.cvtColor(allcolorsImg, cv2.COLOR_BGR2GRAY) |
|
|
|
|
|
ColoredContour, Coloredhierarchy = cv2.findContours(allcolorsImgG, cv2.RETR_TREE, cv2.CHAIN_APPROX_NONE) |
|
|
Coloredhierarchy=Coloredhierarchy[0] |
|
|
for cnt in ColoredContour : |
|
|
Blackmask = np.zeros(img.shape[:2], dtype="uint8") |
|
|
cv2.drawContours(Blackmask,[cnt],0,(255,255,255),20) |
|
|
coloredand=cv2.bitwise_and(allcolorsImg,allcolorsImg,mask=Blackmask) |
|
|
|
|
|
for colors in finalColorArray: |
|
|
getColor=DetectColor(coloredand,colors)[1] |
|
|
|
|
|
pil_image=Image.fromarray(getColor) |
|
|
extrema = pil_image.convert("L").getextrema() |
|
|
if extrema != (0, 0): |
|
|
arraycolor.append(colors) |
|
|
break |
|
|
|
|
|
res = [] |
|
|
[res.append(x) for x in arraycolor if x not in res] |
|
|
|
|
|
return res |
|
|
|
|
|
def getinnerColor(BlackmaskDetected,img,detectedColors,finalColorArray,num1,num2,flag,eachcolor): |
|
|
|
|
|
countBlackMasks=0 |
|
|
xored=detectedColors |
|
|
|
|
|
invertedmask=detectedColors |
|
|
|
|
|
imgc=img.copy() |
|
|
imgNewCopy=img.copy() |
|
|
Blackmask = np.zeros(img.shape[:2], dtype="uint8") |
|
|
for eachcolor in finalColorArray: |
|
|
masked=DetectColor(detectedColors,eachcolor)[0] |
|
|
pil_image=Image.fromarray(masked) |
|
|
extrema = pil_image.convert("L").getextrema() |
|
|
if extrema != (0, 0): |
|
|
cc=detectedColors.copy() |
|
|
|
|
|
ColoredContour, Coloredhierarchy = cv2.findContours(masked, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) |
|
|
|
|
|
for cnt in ColoredContour: |
|
|
|
|
|
area1 = cv2.contourArea(cnt) |
|
|
if (area1 > 1000 ): |
|
|
|
|
|
x, y , width, height = cv2.boundingRect(cnt) |
|
|
|
|
|
|
|
|
|
|
|
cv2.drawContours(cc,[cnt],0,(255,255,255), 3) |
|
|
cv2.drawContours(Blackmask,[cnt] ,0, (255,255,255), 3) |
|
|
|
|
|
cv2.drawContours(cc,[cnt],0,(255,255,255), -1) |
|
|
cv2.drawContours(Blackmask,[cnt] ,0, (255,255,255), -1) |
|
|
|
|
|
cv2.drawContours(BlackmaskDetected,[cnt] ,0, (0,0,0), -1) |
|
|
|
|
|
invertedmask = cv2.bitwise_and(imgc,imgc, mask= Blackmask) |
|
|
xored=cc |
|
|
|
|
|
detectedColors=xored |
|
|
|
|
|
else: |
|
|
countBlackMasks+=1 |
|
|
|
|
|
return xored,invertedmask , BlackmaskDetected |
|
|
|
|
|
def allLevelsofColor(BlackmaskDetected,img,levelonly, invertedmask,color,finalColorArray): |
|
|
|
|
|
|
|
|
firstLevel=levelonly |
|
|
firstLevel1=levelonly |
|
|
print('in') |
|
|
Blackmask = np.zeros(img.shape[:2], dtype="uint8") |
|
|
|
|
|
masked,maskedColor,rgbcolor=DetectColor(invertedmask,color) |
|
|
color=hexRGB(color) |
|
|
color=[color[0],color[1],color[2]] |
|
|
rgbcolor=[rgbcolor[0],rgbcolor[1],rgbcolor[2]] |
|
|
print(rgbcolor,color) |
|
|
pil_image=Image.fromarray(masked) |
|
|
extrema = pil_image.convert("L").getextrema() |
|
|
if extrema != (0, 0): |
|
|
|
|
|
if rgbcolor==color: |
|
|
print('kkkkkkkk') |
|
|
ColoredContour, Coloredhierarchy = cv2.findContours(masked, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE) |
|
|
Coloredhierarchy=Coloredhierarchy[0] |
|
|
for component in zip(ColoredContour,Coloredhierarchy): |
|
|
cnt=component[0] |
|
|
hier=component[1] |
|
|
area1 = cv2.contourArea(cnt) |
|
|
if (area1 > 1000 ): |
|
|
if hier[3]> -1: |
|
|
cv2.drawContours(Blackmask,[cnt],0,(255,255,255), -1) |
|
|
cv2.drawContours(Blackmask,[cnt],0,(0,0,0), 20) |
|
|
cv2.drawContours(BlackmaskDetected,[cnt],0,(255,255,255), -1) |
|
|
|
|
|
firstLevel=cv2.bitwise_and(invertedmask,invertedmask,mask=Blackmask) |
|
|
|
|
|
|
|
|
black_pixels = np.where( |
|
|
(firstLevel[:, :, 0] == 0) & |
|
|
(firstLevel[:, :, 1] == 0) & |
|
|
(firstLevel[:, :, 2] == 0) |
|
|
) |
|
|
|
|
|
|
|
|
firstLevel[black_pixels] = [255, 255, 255] |
|
|
firstLevel1=cv2.bitwise_and(levelonly,firstLevel) |
|
|
|
|
|
|
|
|
|
|
|
for othercolor in finalColorArray: |
|
|
othercolor2=hexRGB(othercolor) |
|
|
othercolor2=[othercolor2[0],othercolor2[1],othercolor2[2]] |
|
|
print(othercolor2,color) |
|
|
if othercolor2!=color: |
|
|
print('anothre') |
|
|
masked0=DetectColor(firstLevel,othercolor)[0] |
|
|
pil_image0=Image.fromarray(masked0) |
|
|
extrema0 = pil_image0.convert("L").getextrema() |
|
|
if extrema != (0, 0): |
|
|
ColoredContour0, Coloredhierarchy0 = cv2.findContours(masked0, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) |
|
|
for cnt in ColoredContour0: |
|
|
area1 = cv2.contourArea(cnt) |
|
|
if (area1 > 1000 ): |
|
|
cv2.drawContours(firstLevel1,[cnt],0,(255,255,255), -1) |
|
|
cv2.drawContours(firstLevel1,[cnt],0,(255,255,255), 10) |
|
|
cv2.drawContours(BlackmaskDetected,[cnt],0,(0,0,0), -1) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return firstLevel1, BlackmaskDetected |
|
|
|
|
|
def getColoredContour(mask,img,finalColorArray,num1,num2,flag,eachcolor): |
|
|
print('uuuuuuuuummmmmmmmmmmmm') |
|
|
ColoredContour, Coloredhierarchy = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE) |
|
|
Coloredhierarchy=Coloredhierarchy[0] |
|
|
|
|
|
imgc= img.copy() |
|
|
|
|
|
detectedColors=np.zeros(img.shape[:2], dtype="uint8") |
|
|
Blackmask = np.zeros(img.shape[:2], dtype="uint8") |
|
|
|
|
|
for component in zip( ColoredContour, Coloredhierarchy): |
|
|
cnt=component[0] |
|
|
hier=component[1] |
|
|
area1 = cv2.contourArea(cnt) |
|
|
if (area1 > 3000 ): |
|
|
|
|
|
if hier[3] >-1: |
|
|
|
|
|
x, y , width, height = cv2.boundingRect(cnt) |
|
|
cv2.drawContours(Blackmask, [cnt], 0,(255,255,255), -1) |
|
|
cv2.drawContours(Blackmask, [cnt], 0,(0,0,0), 10) |
|
|
|
|
|
detectedColors = cv2.bitwise_and(imgc,imgc, mask= Blackmask) |
|
|
pil_image=Image.fromarray(detectedColors) |
|
|
extrema = pil_image.convert("L").getextrema() |
|
|
if extrema == (0, 0) : |
|
|
break |
|
|
|
|
|
levelOnly,invertedmask,BlackmaskDetected=getinnerColor(Blackmask,img,detectedColors,finalColorArray,num1,num2,flag,eachcolor) |
|
|
firstLevel1, BlackmaskDetected1= allLevelsofColor(BlackmaskDetected,img,levelOnly, invertedmask,eachcolor,finalColorArray) |
|
|
|
|
|
print('AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA') |
|
|
return firstLevel1,invertedmask, BlackmaskDetected1 |
|
|
|
|
|
"""# contours""" |
|
|
|
|
|
def findContoursFullImage(green2,img,number,finalColorArray,num1,num2,flag,color=[0,0,0]): |
|
|
if number == 0: |
|
|
thresh=preprocess(img,number,green2) |
|
|
|
|
|
contourss, hierarchy = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) |
|
|
return contourss |
|
|
else: |
|
|
mask, detectedColors, rgbcolor =DetectColor(img,color) |
|
|
pil_image=Image.fromarray(mask) |
|
|
extrema = pil_image.convert("L").getextrema() |
|
|
if extrema != (0, 0): |
|
|
coloredregions,invertedmask,BlackmaskDetected1=getColoredContour(mask,img,finalColorArray,num1,num2,flag,color) |
|
|
|
|
|
thresh=preprocess(coloredregions,number,green2) |
|
|
x=cv2.bitwise_and(thresh,thresh,mask=BlackmaskDetected1) |
|
|
contourss, hierarchy = cv2.findContours(x, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) |
|
|
return contourss,rgbcolor ,invertedmask |
|
|
|
|
|
else: |
|
|
|
|
|
thresh=preprocess(img,number,green2) |
|
|
|
|
|
contourss, hierarchy = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) |
|
|
hierarchy = hierarchy[0] |
|
|
return contourss,color ,mask |
|
|
|
|
|
|
|
|
|
|
|
def StraightenImage(contour,imgArea): |
|
|
rect = cv2.minAreaRect(contour) |
|
|
|
|
|
(center, (width, height), angleR) = cv2.minAreaRect(contour) |
|
|
|
|
|
box = cv2.boxPoints(rect) |
|
|
box = np.int0(box) |
|
|
|
|
|
|
|
|
width = int(rect[1][0]) |
|
|
height = int(rect[1][1]) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return angleR,width,height |
|
|
|
|
|
def getAreasPerimeter(green2,img,number,num1,num2,flag,finalColorArray,color=[0,0,0]): |
|
|
appended=[] |
|
|
if number==0: |
|
|
contourss=findContoursFullImage(green2,img,number,finalColorArray,num1,num2,flag,color) |
|
|
else: |
|
|
contourss=findContoursFullImage(green2,img,number,finalColorArray,num1,num2,flag,color)[0] |
|
|
|
|
|
for contour in contourss: |
|
|
|
|
|
area1 = cv2.contourArea(contour) |
|
|
perimeter1 = cv2.arcLength(contour, True) |
|
|
x, y , width, height = cv2.boundingRect(contour) |
|
|
|
|
|
angleR,widthR ,heightR= StraightenImage(contour,img) |
|
|
|
|
|
if (angleR != 90.0 and angleR != -90.0 and angleR != 0.0 and angleR != -0.0 ): |
|
|
width=widthR |
|
|
height=heightR |
|
|
if (area1 > 4000 ): |
|
|
if num1!=0 and num2!=0: |
|
|
if flag=='area': |
|
|
|
|
|
|
|
|
areaa=round(area1*(num1/num2),3) |
|
|
appended.append([areaa,width,height]) |
|
|
|
|
|
else: |
|
|
perimeter=round(perimeter1*(num1/num2),3) |
|
|
appended.append([perimeter,width,height]) |
|
|
|
|
|
return appended |
|
|
|
|
|
|
|
|
def FillDictionary(green2,SimilarAreaDictionary,img,number,num1,num2,flag,finalColorArray,rgbcolor=[0,0,0],color=[0,0,0]): |
|
|
|
|
|
print('wttttt') |
|
|
areas_Perimeters=sorted(getAreasPerimeter(green2,img,number,num1,num2,flag,finalColorArray,color) ) |
|
|
print(areas_Perimeters) |
|
|
indices=[] |
|
|
colorRanges=[[255,153,153],[51,255,51],[201,56,147],[255,0,0],[255,0,255],[0,102,204],[102,0,102],[153,0,76],[200,92,135],[52,161,99],[235,250,24],[40,30,170],[98,149,63],[100,30,179],[200,55,67],[150,80,200],[0,102,102],[250,28,191],[101,27,101],[230,150,76],[3,65,127],[114,39,39],[250,36,100],[180,30,40],[10,250,60],[140,30,253],[114,58,245],[47,255,255],[18,236,206],[225,105,29],[189,65,121],[206,204,48],[126,7,247],[3,168,251]] |
|
|
print(colorRanges[0]) |
|
|
print(colorRanges[0][0],colorRanges[0][1], colorRanges[0][2]) |
|
|
colorsUsed=[] |
|
|
for i in range(len(areas_Perimeters)): |
|
|
print(colorRanges) |
|
|
|
|
|
item1 = areas_Perimeters[i][0] |
|
|
width1 = areas_Perimeters[i][1] |
|
|
height1 = areas_Perimeters[i][2] |
|
|
widthMin= width1-5 |
|
|
widthMax= width1+5 |
|
|
heightMin=height1-5 |
|
|
heightMax= height1+5 |
|
|
areaPerimeterMin= round(item1,1) - 0.3 |
|
|
areaPerimeterMax= round(item1,1) + 0.3 |
|
|
|
|
|
if color != [0,0,0]: |
|
|
mydata=[[rgbcolor[0],rgbcolor[1],rgbcolor[2] ],round(item1,1),width1,height1,0, 1,0,0,0,0] |
|
|
|
|
|
|
|
|
else: |
|
|
|
|
|
mydata=[' ', round(item1,1),width1,height1,0, 1,0,0,0,0] |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
myindex= SimilarAreaDictionary.index[((SimilarAreaDictionary['Rounded'] >=areaPerimeterMin) &(SimilarAreaDictionary['Rounded']<=areaPerimeterMax) )].tolist() |
|
|
print(myindex) |
|
|
|
|
|
|
|
|
if color!= [0,0,0]: |
|
|
|
|
|
checkifColorExists=0 |
|
|
for i in myindex: |
|
|
if SimilarAreaDictionary['Color'].loc[i]==[rgbcolor[0],rgbcolor[1],rgbcolor[2]] and ( SimilarAreaDictionary['Rounded'].loc[i] >= areaPerimeterMin and SimilarAreaDictionary['Rounded'].loc[i] <= areaPerimeterMax) : |
|
|
if (SimilarAreaDictionary['Width'].loc[i] <=widthMax and SimilarAreaDictionary['Width'].loc[i] >= widthMin) and (SimilarAreaDictionary['Height'].loc[i] <= heightMax and SimilarAreaDictionary['Height'].loc[i] >= heightMin ) or (SimilarAreaDictionary['Width'].loc[i] <=heightMax and SimilarAreaDictionary['Width'].loc[i] >= heightMin) and (SimilarAreaDictionary['Height'].loc[i] <= widthMax and SimilarAreaDictionary['Height'].loc[i] >= widthMin ) : |
|
|
checkifColorExists=1 |
|
|
SimilarAreaDictionary['Occurences'].loc[i]+=1 |
|
|
if checkifColorExists==0: |
|
|
SimilarAreaDictionary.loc[len(SimilarAreaDictionary)] =mydata |
|
|
|
|
|
else: |
|
|
|
|
|
|
|
|
checkifColorExists=0 |
|
|
for i in myindex: |
|
|
if ( SimilarAreaDictionary['Rounded'].loc[i] <= areaPerimeterMax and SimilarAreaDictionary['Rounded'].loc[i] >= areaPerimeterMin) : |
|
|
|
|
|
if (SimilarAreaDictionary['Width'].loc[i] <=widthMax and SimilarAreaDictionary['Width'].loc[i] >= widthMin) and (SimilarAreaDictionary['Height'].loc[i] <= heightMax and SimilarAreaDictionary['Height'].loc[i] >= heightMin ) or (SimilarAreaDictionary['Width'].loc[i] <=heightMax and SimilarAreaDictionary['Width'].loc[i] >= heightMin) and (SimilarAreaDictionary['Height'].loc[i] <= widthMax and SimilarAreaDictionary['Height'].loc[i] >= widthMin ) : |
|
|
checkifColorExists=1 |
|
|
SimilarAreaDictionary['Occurences'].loc[i]+=1 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if checkifColorExists==0: |
|
|
SimilarAreaDictionary.loc[len(SimilarAreaDictionary)] =mydata |
|
|
s= SimilarAreaDictionary |
|
|
for i in range(len(SimilarAreaDictionary)): |
|
|
SimilarAreaDictionary.loc[i, "R"] = colorRanges[i][0] |
|
|
SimilarAreaDictionary.loc[i, "G"] = colorRanges[i][1] |
|
|
SimilarAreaDictionary.loc[i, "B"] = colorRanges[i][2] |
|
|
|
|
|
|
|
|
|
|
|
colorsUsed.append(colorRanges[i]) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return SimilarAreaDictionary, colorsUsed |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def drawAllContours(plan,green2,img,number,finalColorArray,num1,num2,flag): |
|
|
|
|
|
|
|
|
areasinImage=[] |
|
|
totaldf=pd.DataFrame() |
|
|
imgArea1= img.copy() |
|
|
imgPerimeter1=img.copy() |
|
|
imgtransparent1=img.copy() |
|
|
|
|
|
Blackmask = np.zeros(img.shape[:2], dtype="uint8") |
|
|
|
|
|
invertedmask=img |
|
|
|
|
|
allpoints=[] |
|
|
|
|
|
if number ==220: |
|
|
finalColorArray= colorOrder(img,finalColorArray) |
|
|
if flag== 'area': |
|
|
SimilarAreaDictionary= pd.DataFrame(columns=['Color','Rounded','Width','Height','Area','Occurences','Total Area' , 'R','G','B']) |
|
|
else: |
|
|
SimilarAreaDictionary= pd.DataFrame(columns=['Color','Rounded','Width','Height','Perimeter','Occurences','Total Perimeter' ,'R','G','B']) |
|
|
firstcolor=finalColorArray[0] |
|
|
|
|
|
counter=0 |
|
|
maskDone=img.copy() |
|
|
|
|
|
for eachcolor in finalColorArray: |
|
|
|
|
|
if eachcolor==firstcolor: |
|
|
counter+=1 |
|
|
|
|
|
contourss,rgbcolor,invertedmask=findContoursFullImage(green2,maskDone,number,finalColorArray,num1,num2,flag,eachcolor) |
|
|
SimilarAreaDictionary ,colorsUsed= FillDictionary(green2,SimilarAreaDictionary,maskDone,number,num1,num2,flag,finalColorArray,rgbcolor,eachcolor) |
|
|
|
|
|
a = SimilarAreaDictionary.to_numpy() |
|
|
|
|
|
for contour in contourss: |
|
|
shape=[] |
|
|
|
|
|
area1 = cv2.contourArea(contour) |
|
|
perimeter1 = cv2.arcLength(contour, True) |
|
|
if (area1 > 4000 ): |
|
|
angleR,widthR ,heightR= StraightenImage(contour,imgArea1) |
|
|
rect = cv2.minAreaRect(contour) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
x, y , width, height = cv2.boundingRect(contour) |
|
|
|
|
|
approx = cv2.approxPolyDP(contour, 0.005 * perimeter1, True) |
|
|
for point in approx: |
|
|
x1, y1 = point[0] |
|
|
|
|
|
cv2.circle(imgArea1, (x1, y1), 4, (0, 255, 0), -1) |
|
|
|
|
|
|
|
|
if (angleR != 90.0 and angleR != -90.0 and angleR != 0.0 and angleR != -0.0 ): |
|
|
width=widthR |
|
|
height=heightR |
|
|
|
|
|
widthMin= width-5 |
|
|
widthMax= width+5 |
|
|
heightMin=height-5 |
|
|
heightMax= height+5 |
|
|
if num1 !=0 and num2!=0: |
|
|
widthh=round(width*(num1/num2),3) |
|
|
heightt=round(height*(num1/num2),3) |
|
|
if flag=='area': |
|
|
addedMargin=area1+perimeter1*2 |
|
|
areaa=round(addedMargin* (num1/(num2+perimeter1*2) ), 3) |
|
|
elif flag=='perimeter': |
|
|
perimeterr=round(perimeter1* (num1/num2 ), 3) |
|
|
else: |
|
|
areaa=area1 |
|
|
perimeterr=perimeter1 |
|
|
|
|
|
if flag=='area': |
|
|
areaPerimeterMin= round(areaa,1) - 0.3 |
|
|
areaPerimeterMax= round(areaa,1) + 0.3 |
|
|
masked=SimilarAreaDictionary.loc[SimilarAreaDictionary.index[((SimilarAreaDictionary['Rounded'] >=areaPerimeterMin) &(SimilarAreaDictionary['Rounded']<=areaPerimeterMax) )]] |
|
|
|
|
|
|
|
|
passed=0 |
|
|
for i, row in masked.iterrows(): |
|
|
if passed ==0: |
|
|
if SimilarAreaDictionary['Color'].loc[i] == [rgbcolor[0],rgbcolor[1],rgbcolor[2]] and ( SimilarAreaDictionary['Rounded'].loc[i] <= areaPerimeterMax and SimilarAreaDictionary['Rounded'].loc[i] >= areaPerimeterMin) : |
|
|
if (SimilarAreaDictionary['Width'].loc[i] <=widthMax and SimilarAreaDictionary['Width'].loc[i] >= widthMin) and (SimilarAreaDictionary['Height'].loc[i] <= heightMax and SimilarAreaDictionary['Height'].loc[i] >= heightMin ) or (SimilarAreaDictionary['Width'].loc[i] <=heightMax and SimilarAreaDictionary['Width'].loc[i] >= heightMin) and (SimilarAreaDictionary['Height'].loc[i] <= widthMax and SimilarAreaDictionary['Height'].loc[i] >= widthMin ) : |
|
|
SimilarAreaDictionary['Total Area'].loc[i]+=areaa |
|
|
SimilarAreaDictionary['Area'].loc[i]=areaa |
|
|
passed=1 |
|
|
|
|
|
cv2.drawContours(imgArea1, [contour], 0, (int(rgbcolor[2]), int(rgbcolor[1]), int(rgbcolor[0])), -1) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
cv2.putText(imgtransparent1,'Area= '+str(areaa) + ' m', (x+50,y-10) ,cv2.FONT_HERSHEY_SIMPLEX, 0.6, (50, 50, 255), 2) |
|
|
areasinImage.append(areaa) |
|
|
|
|
|
elif flag=='perimeter': |
|
|
areaPerimeterMin= round(perimeterr,1) - 0.3 |
|
|
areaPerimeterMax= round(perimeterr,1) + 0.3 |
|
|
masked=SimilarAreaDictionary.loc[SimilarAreaDictionary.index[((SimilarAreaDictionary['Rounded'] >=areaPerimeterMin) &(SimilarAreaDictionary['Rounded']<=areaPerimeterMax) )]] |
|
|
passed=0 |
|
|
|
|
|
for i, row in masked.iterrows(): |
|
|
if passed ==0: |
|
|
if SimilarAreaDictionary['Color'].loc[i] == [rgbcolor[0],rgbcolor[1],rgbcolor[2]] and ( SimilarAreaDictionary['Rounded'].loc[i] <= areaPerimeterMax and SimilarAreaDictionary['Rounded'].loc[i] >= areaPerimeterMin) : |
|
|
if (SimilarAreaDictionary['Width'].loc[i] <=widthMax and SimilarAreaDictionary['Width'].loc[i] >= widthMin) and (SimilarAreaDictionary['Height'].loc[i] <= heightMax and SimilarAreaDictionary['Height'].loc[i] >= heightMin ) or (SimilarAreaDictionary['Width'].loc[i] <=heightMax and SimilarAreaDictionary['Width'].loc[i] >= heightMin) and (SimilarAreaDictionary['Height'].loc[i] <= widthMax and SimilarAreaDictionary['Height'].loc[i] >= widthMin ) : |
|
|
SimilarAreaDictionary['Total Perimeter'].loc[i]+=perimeterr |
|
|
SimilarAreaDictionary['Perimeter'].loc[i]=perimeterr |
|
|
passed=1 |
|
|
cv2.drawContours(imgPerimeter1, [contour], 0, (int(rgbcolor[2]), int(rgbcolor[1]), int(rgbcolor[0])), 3) |
|
|
cv2.putText(imgPerimeter1,'Perimeter'+str(perimeterr), (x+50,y-10) ,cv2.FONT_HERSHEY_SIMPLEX, 0.6, (50, 50, 255), 2) |
|
|
|
|
|
|
|
|
areasinImage.append(perimeterr) |
|
|
|
|
|
|
|
|
for i,row in SimilarAreaDictionary.iterrows(): |
|
|
|
|
|
if row[3] not in areasinImage: |
|
|
SimilarAreaDictionary = SimilarAreaDictionary.drop(SimilarAreaDictionary.loc[SimilarAreaDictionary.index==i].index) |
|
|
|
|
|
|
|
|
else: |
|
|
|
|
|
if flag=='area': |
|
|
SimilarAreaDictionary= pd.DataFrame(columns=['Color','Rounded','Width','Height','Area','Occurences','Total Area','R','G','B']) |
|
|
|
|
|
else: |
|
|
SimilarAreaDictionary= pd.DataFrame(columns=['Color','Rounded','Width','Height','Perimeter','Occurences','Total Perimeter','R','G','B']) |
|
|
contourss=findContoursFullImage(green2,img,number,finalColorArray,num1,num2,flag) |
|
|
|
|
|
SimilarAreaDictionary , colorsUsed= FillDictionary(green2,SimilarAreaDictionary,img,number,num1,num2,flag,finalColorArray) |
|
|
|
|
|
for contour in contourss: |
|
|
|
|
|
area1 = cv2.contourArea(contour) |
|
|
perimeter1 = cv2.arcLength(contour, True) |
|
|
if (area1 >4000 ): |
|
|
|
|
|
angleR,widthR ,heightR= StraightenImage(contour,imgArea1) |
|
|
x, y , width, height = cv2.boundingRect(contour) |
|
|
if (angleR != 90.0 and angleR != -90.0 and angleR != 0.0 and angleR != -0.0 ): |
|
|
width=widthR |
|
|
height=heightR |
|
|
|
|
|
widthMin= width-5 |
|
|
widthMax= width+5 |
|
|
heightMin=height-5 |
|
|
heightMax= height+5 |
|
|
if num1 !=0 and num2!=0: |
|
|
if flag=='area': |
|
|
|
|
|
|
|
|
areaa=round(area1*(num1/num2),3) |
|
|
elif flag=='perimeter': |
|
|
perimeterr=round(perimeter1* (num1/num2 ), 3) |
|
|
else: |
|
|
areaa=area1 |
|
|
perimeterr=perimeter1 |
|
|
if flag=='area': |
|
|
areaPerimeterMin= round(areaa,1) - 0.3 |
|
|
areaPerimeterMax= round(areaa,1) + 0.3 |
|
|
masked=SimilarAreaDictionary.loc[SimilarAreaDictionary.index[((SimilarAreaDictionary['Rounded'] >=areaPerimeterMin) &(SimilarAreaDictionary['Rounded']<=areaPerimeterMax) )]] |
|
|
passed=0 |
|
|
|
|
|
for i, row in masked.iterrows(): |
|
|
if passed ==0: |
|
|
if ( SimilarAreaDictionary['Rounded'].loc[i] <= areaPerimeterMax and SimilarAreaDictionary['Rounded'].loc[i] >= areaPerimeterMin) : |
|
|
if (SimilarAreaDictionary['Width'].loc[i] <=widthMax and SimilarAreaDictionary['Width'].loc[i] >= widthMin) and (SimilarAreaDictionary['Height'].loc[i] <= heightMax and SimilarAreaDictionary['Height'].loc[i] >= heightMin ) or (SimilarAreaDictionary['Width'].loc[i] <=heightMax and SimilarAreaDictionary['Width'].loc[i] >= heightMin) and (SimilarAreaDictionary['Height'].loc[i] <= widthMax and SimilarAreaDictionary['Height'].loc[i] >= widthMin ) : |
|
|
SimilarAreaDictionary['Total Area'].loc[i]+=areaa |
|
|
SimilarAreaDictionary['Area'].loc[i]=areaa |
|
|
passed=1 |
|
|
cv2.drawContours(imgArea1, [contour], 0, ( int(SimilarAreaDictionary['B'].loc[i]), int(SimilarAreaDictionary['G'].loc[i]), int(SimilarAreaDictionary['R'].loc[i])), -1) |
|
|
cv2.putText(imgtransparent1,'Area= '+str(areaa) + ' m', (x+50,y-10) ,cv2.FONT_HERSHEY_SIMPLEX, 0.6, (50, 50, 255), 2) |
|
|
cv2.drawContours(imgArea1, [contour], 0, (0, 0, 255), 4) |
|
|
elif flag=='perimeter': |
|
|
areaPerimeterMin= round(perimeterr,1) - 0.3 |
|
|
areaPerimeterMax= round(perimeterr,1) + 0.3 |
|
|
masked=SimilarAreaDictionary.loc[SimilarAreaDictionary.index[((SimilarAreaDictionary['Rounded'] >=areaPerimeterMin) &(SimilarAreaDictionary['Rounded']<=areaPerimeterMax) )]] |
|
|
passed=0 |
|
|
|
|
|
for i, row in masked.iterrows(): |
|
|
if passed ==0: |
|
|
if ( SimilarAreaDictionary['Rounded'].loc[i] <= areaPerimeterMax and SimilarAreaDictionary['Rounded'].loc[i] >= areaPerimeterMin) : |
|
|
if (SimilarAreaDictionary['Width'].loc[i] <=widthMax and SimilarAreaDictionary['Width'].loc[i] >= widthMin) and (SimilarAreaDictionary['Height'].loc[i] <= heightMax and SimilarAreaDictionary['Height'].loc[i] >= heightMin ) or (SimilarAreaDictionary['Width'].loc[i] <=heightMax and SimilarAreaDictionary['Width'].loc[i] >= heightMin) and (SimilarAreaDictionary['Height'].loc[i] <= widthMax and SimilarAreaDictionary['Height'].loc[i] >= widthMin ) : |
|
|
SimilarAreaDictionary['Total Perimeter'].loc[i]+=perimeterr |
|
|
SimilarAreaDictionary['Perimeter'].loc[i]=perimeterr |
|
|
passed=1 |
|
|
cv2.drawContours(imgPerimeter1, [contour], 0, (0, 0, 255), 4) |
|
|
|
|
|
|
|
|
cv2.putText(imgPerimeter1,'Perimeter='+str(perimeterr), (x+50,y-10) ,cv2.FONT_HERSHEY_SIMPLEX, 0.6, (50, 50, 255), 2) |
|
|
cv2.drawContours(imgArea1, [contour], 0, (0, 0, 255), 4) |
|
|
|
|
|
|
|
|
alpha = 0.4 |
|
|
image_new1 = cv2.addWeighted(imgArea1, alpha, imgtransparent1, 1 - alpha, 0) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
SimilarAreaDictionary.drop(['Rounded', 'Width','Height','R','G','B'], axis=1, inplace=True) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return imgPerimeter1,image_new1,SimilarAreaDictionary , colorsUsed |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def retrieveMCCol(gc): |
|
|
ws=gc.open_by_key('1A8VtqLFhe2NXPxIjfAilbxF9xV2eSzZ-yZ9GP8_5jSo') |
|
|
worksheet = ws.worksheet(0) |
|
|
mcT_Names=worksheet.get_col(1) |
|
|
newMcTNames=[] |
|
|
for i in mcT_Names: |
|
|
if i != '': |
|
|
newMcTNames.append(i) |
|
|
return newMcTNames |
|
|
|
|
|
def getdropdownValues(): |
|
|
SCOPES = [ |
|
|
'https://www.googleapis.com/auth/spreadsheets', |
|
|
'https://www.googleapis.com/auth/drive' |
|
|
] |
|
|
credentials = service_account.Credentials.from_service_account_file('credentials.json', scopes=SCOPES) |
|
|
spreadsheet_service = build('sheets', 'v4', credentials=credentials) |
|
|
drive_service = build('drive', 'v3', credentials=credentials) |
|
|
gc = pygsheets.authorize(custom_credentials=credentials, client_secret='credentials.json') |
|
|
|
|
|
dropdownValues=[] |
|
|
allIds=gc.spreadsheet_ids() |
|
|
for spreadsheetId in allIds: |
|
|
if spreadsheetId != '1A8VtqLFhe2NXPxIjfAilbxF9xV2eSzZ-yZ9GP8_5jSo': |
|
|
print(spreadsheetId) |
|
|
ws=gc.open_by_key('1A8VtqLFhe2NXPxIjfAilbxF9xV2eSzZ-yZ9GP8_5jSo') |
|
|
worksheet = ws.worksheet(0) |
|
|
response = spreadsheet_service.spreadsheets().get( |
|
|
spreadsheetId=spreadsheetId, fields='*', |
|
|
ranges='A2:A60',includeGridData=True).execute() |
|
|
r=list(response['sheets'][0]['data'][0]['rowData'][0]['values'][0]) |
|
|
print(r) |
|
|
if 'dataValidation' in r: |
|
|
print('yes') |
|
|
colvals= response['sheets'][0]['data'][0]['rowData'][0]['values'][0]['dataValidation'] |
|
|
colvalsList=list(colvals.items()) |
|
|
|
|
|
lengthVals=len(colvalsList[0][1]['values']) |
|
|
for i in range(lengthVals): |
|
|
dictVal=(colvalsList[0][1]['values'][i].values()) |
|
|
|
|
|
x=[*dictVal][0] |
|
|
|
|
|
if x not in dropdownValues: |
|
|
dropdownValues.append(*dictVal) |
|
|
print(dropdownValues) |
|
|
|
|
|
worksheet.update_col(index=1, values=dropdownValues) |
|
|
|
|
|
return dropdownValues |
|
|
|
|
|
def createGoogleSheet(plan): |
|
|
print('create1') |
|
|
|
|
|
|
|
|
SCOPES = [ |
|
|
'https://www.googleapis.com/auth/spreadsheets', |
|
|
'https://www.googleapis.com/auth/drive' |
|
|
] |
|
|
credentials = service_account.Credentials.from_service_account_file('credentials.json', scopes=SCOPES) |
|
|
spreadsheet_service = build('sheets', 'v4', credentials=credentials) |
|
|
drive_service = build('drive', 'v3', credentials=credentials) |
|
|
gc = pygsheets.authorize(custom_credentials=credentials, client_secret='credentials.json') |
|
|
|
|
|
|
|
|
spreadsheet_details = { |
|
|
'properties': { |
|
|
'title': 'Legend of ' + str(plan) |
|
|
} |
|
|
} |
|
|
sheet = spreadsheet_service.spreadsheets().create(body=spreadsheet_details, |
|
|
fields='spreadsheetId').execute() |
|
|
|
|
|
spreadsheetId = sheet.get('spreadsheetId') |
|
|
|
|
|
permission1 = { |
|
|
'type': 'anyone', |
|
|
'role': 'writer', |
|
|
|
|
|
} |
|
|
drive_service.permissions().create(fileId=spreadsheetId, body=permission1).execute() |
|
|
print('createee') |
|
|
return spreadsheetId,spreadsheet_service,gc |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def legendGoogleSheets(path,SimilarAreaDictionary,colorsUsed, spreadsheetId,spreadsheet_service,gc): |
|
|
|
|
|
|
|
|
|
|
|
titles=gc.spreadsheet_titles() |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
print('creating new sheeet') |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
ws=gc.open_by_key(spreadsheetId) |
|
|
worksheet = ws.worksheet(0) |
|
|
|
|
|
|
|
|
columnsLen=len(SimilarAreaDictionary.columns.values.tolist()) |
|
|
lastUsedCol=columnsLen+1 |
|
|
|
|
|
rowsLen=len(SimilarAreaDictionary.values.tolist()) |
|
|
lastUsedRow=rowsLen+1 |
|
|
|
|
|
worksheet.update_row(1,SimilarAreaDictionary.columns.values.tolist() ,col_offset=1) |
|
|
worksheet.append_table(SimilarAreaDictionary.values.tolist(), dimension='ROWS' ) |
|
|
|
|
|
worksheet.update_col(index=1,values=['MC-Template Names'],row_offset=0) |
|
|
|
|
|
|
|
|
firstcell=worksheet.cell((2,1)) |
|
|
firstcellNotation=str(firstcell.address.label) |
|
|
|
|
|
lastcell=worksheet.cell((rowsLen+1,1)) |
|
|
lastcellNotation=str(lastcell.address.label) |
|
|
|
|
|
lastcolumn=worksheet.cell((1,lastUsedCol)) |
|
|
lastcolumnNotation=str(lastcolumn.address.label) |
|
|
|
|
|
|
|
|
mcT_Names=retrieveMCCol(gc) |
|
|
worksheet.set_data_validation(firstcellNotation,lastcellNotation, condition_type='ONE_OF_LIST', condition_values=mcT_Names, showCustomUi=True) |
|
|
|
|
|
model_cell =worksheet.cell('A1') |
|
|
model_cell.set_text_format('bold', True) |
|
|
pygsheets.DataRange('A1',lastcolumnNotation, worksheet=worksheet).apply_format(model_cell) |
|
|
worksheet.adjust_column_width(start=1,end=lastUsedCol) |
|
|
|
|
|
|
|
|
sheetId = '0' |
|
|
for i in range(len(colorsUsed)): |
|
|
|
|
|
print(colorsUsed[i]) |
|
|
r,g,b=colorsUsed[i] |
|
|
body = { |
|
|
"requests": [ |
|
|
{ |
|
|
"updateCells": { |
|
|
"range": { |
|
|
"sheetId": sheetId, |
|
|
"startRowIndex": i+1, |
|
|
|
|
|
"startColumnIndex":1, |
|
|
|
|
|
|
|
|
}, |
|
|
|
|
|
"rows": [ |
|
|
{ |
|
|
"values": [ |
|
|
{ |
|
|
"userEnteredFormat": { |
|
|
"backgroundColor": { |
|
|
|
|
|
"red": r/255, |
|
|
"green": g/255, |
|
|
"blue": b/255, |
|
|
|
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
} |
|
|
] |
|
|
} |
|
|
], |
|
|
"fields": "userEnteredFormat.backgroundColor", |
|
|
|
|
|
} |
|
|
} |
|
|
] |
|
|
} |
|
|
res = spreadsheet_service.spreadsheets().batchUpdate(spreadsheetId=spreadsheetId, body=body).execute() |
|
|
spreadsheet_url = "https://docs.google.com/spreadsheets/d/%s" % spreadsheetId |
|
|
print(spreadsheet_url) |
|
|
|
|
|
|
|
|
return gc,spreadsheet_service,spreadsheetId , spreadsheet_url |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def MainFunc( spreadsheetId,spreadsheet_service,gc,plan,green2,img,dp,finalColorArray,number,num1,num2,flag): |
|
|
|
|
|
imgPerimeter1,image_new1,Df2,colorsUsed=drawAllContours(plan,green2,img,number,finalColorArray,num1,num2,flag) |
|
|
gc,spreadsheet_service,spreadsheetId ,spreadsheet_url =legendGoogleSheets(plan,Df2,colorsUsed, spreadsheetId,spreadsheet_service,gc) |
|
|
|
|
|
|
|
|
Df2=Df2.T |
|
|
Df2.loc['MC-Template-Name']='' |
|
|
Df2.loc['Unit'] = str(dp) |
|
|
Df2 = Df2.astype(str) |
|
|
if (number ==220): |
|
|
if flag=='area': |
|
|
Df2=Df2.reindex(['MC-Template-Name','Area','Color', 'Occurences', 'Total Area', 'Unit']) |
|
|
else: |
|
|
Df2=Df2.reindex(['MC-Template-Name','Perimeter','Color', 'Occurences', 'Total Perimeter', 'Unit']) |
|
|
else: |
|
|
if flag=='area': |
|
|
Df2=Df2.reindex(['MC-Template-Name','Area', 'Occurences', 'Total Area','Color', 'Unit']) |
|
|
else: |
|
|
Df2=Df2.reindex(['MC-Template-Name','Perimeter', 'Occurences', 'Total Perimeter','Color', 'Unit']) |
|
|
|
|
|
|
|
|
|
|
|
return Df2, imgPerimeter1,image_new1 , spreadsheet_url |
|
|
|
|
|
def PickColorContours( spreadsheetId,spreadsheet_service,gc,plan,dp,img,radioButton,radioButton1, color,color1,color2,color3,color4,color5,color6,color7,color8,num1=0,num2=0): |
|
|
print(type(img)) |
|
|
green2=allpreSteps(img) |
|
|
|
|
|
colorArray=[color,color1,color2,color3,color4,color5,color6,color7,color8] |
|
|
finalColorArray=[] |
|
|
for c in colorArray: |
|
|
checkcolor=c.lstrip('#') |
|
|
if checkcolor == '000000': |
|
|
continue |
|
|
else: |
|
|
finalColorArray.append(c) |
|
|
if num1==0 and num2 ==0 : |
|
|
if radioButton=="Measure Full Image" : |
|
|
|
|
|
if radioButton1=='Area': |
|
|
imgPerimeter1,image_new1,df ,colorsUsed =drawAllContours(plan,green2,img,0,finalColorArray,num1,num2,'area') |
|
|
return image_new1 |
|
|
else: |
|
|
imgPerimeter1,image_new1,df ,colorsUsed =drawAllContours(plan,green2,img,0,finalColorArray,num1,num2,'perimeter') |
|
|
return imgPerimeter1 |
|
|
else: |
|
|
if radioButton1=='Area': |
|
|
imgPerimeter1,image_new1,df ,colorsUsed =drawAllContours(plan,green2,img,220,finalColorArray,num1,num2,'area') |
|
|
return image_new1 |
|
|
else: |
|
|
imgPerimeter1,image_new1,df ,colorsUsed =drawAllContours(plan,green2,img,220,finalColorArray,num1,num2,'perimeter') |
|
|
return imgPerimeter1 |
|
|
else: |
|
|
if radioButton=="Measure Full Image": |
|
|
if radioButton1=='Area': |
|
|
Dictionary, imgPerimeter1,image_new1 ,spreadsheet_url =MainFunc( spreadsheetId,spreadsheet_service,gc,plan,green2,img,dp,finalColorArray,0,num1,num2,'area') |
|
|
else: |
|
|
Dictionary, imgPerimeter1,image_new1 ,spreadsheet_url=MainFunc( spreadsheetId,spreadsheet_service,gc,plan,green2,img,dp,finalColorArray,0,num1,num2,'perimeter') |
|
|
|
|
|
else: |
|
|
if radioButton1=='Area': |
|
|
Dictionary, imgPerimeter1,image_new1 ,spreadsheet_url=MainFunc( spreadsheetId,spreadsheet_service,gc,plan,green2,img,dp,finalColorArray,220,num1,num2,'area') |
|
|
else: |
|
|
Dictionary, imgPerimeter1,image_new1 ,spreadsheet_url=MainFunc( spreadsheetId,spreadsheet_service,gc,plan,green2,img,dp,finalColorArray,220,num1,num2,'perimeter') |
|
|
|
|
|
Dictionary=Dictionary.T |
|
|
|
|
|
|
|
|
|
|
|
if (radioButton1=='Area'): |
|
|
return image_new1,Dictionary ,spreadsheet_url |
|
|
return imgPerimeter1,Dictionary ,spreadsheet_url |
|
|
|
|
|
''' General measurement function''' |
|
|
def getMeasurement(plan,SaveOP,check1, dp,in2,in3,in4,in5,in6,in7,in8,in9,in10,in11,in12,num1=0,num2=0): |
|
|
spreadsheetId,spreadsheet_service,gc=createGoogleSheet(plan) |
|
|
if plan==None: |
|
|
area,perim,df=None,None,None |
|
|
elif 'foundation' in plan: |
|
|
plan1='dropbox_plans/'+str(plan) |
|
|
img=plan2img(plan1) |
|
|
area,perim,df=IsolatedFoundations(img) |
|
|
area,perim,df=img,None,None |
|
|
elif 'piles' or 'pc' in plan: |
|
|
|
|
|
plan1='dropbox_plans/'+str(plan) |
|
|
|
|
|
img=plan2img(plan1) |
|
|
|
|
|
img = cv2.cvtColor(img, cv2.COLOR_RGB2BGR) |
|
|
|
|
|
|
|
|
if num1!=0 and num2!=0: |
|
|
imgPerimeter1,Dictionary , spreadsheet_url = PickColorContours( spreadsheetId,spreadsheet_service,gc,plan1,dp,img,in2,in3,in4,in5,in6,in7,in8,in9,in10,in11,in12,num1,num2) |
|
|
imgPerimeter1= cv2.cvtColor(imgPerimeter1, cv2.COLOR_RGB2BGR) |
|
|
if SaveOP: |
|
|
pushToDropbox(plan,imgPerimeter1,Dictionary) |
|
|
if check1: |
|
|
exportToExcel(plan,Dictionary) |
|
|
|
|
|
return imgPerimeter1,Dictionary , gr.HTML.update( """Click <a href=%s target="_blank"> on this Google Sheet </a> to continue to the Legend.""" %spreadsheet_url) |
|
|
|
|
|
else: |
|
|
area=PickColorContours( spreadsheetId,spreadsheet_service,gc,plan1,dp,img,in2,in3,in4,in5,in6,in7,in8,in9,in10,in11,in12) |
|
|
area = cv2.cvtColor(area, cv2.COLOR_BGR2RGB) |
|
|
|
|
|
|
|
|
return area |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def update_dropdown(project): |
|
|
|
|
|
plans_inrepo=os.listdir('dropbox_plans') |
|
|
|
|
|
matches=[] |
|
|
if project==None: |
|
|
drop=gr.Dropdown.update(choices=matches) |
|
|
else: |
|
|
for x in plans_inrepo: |
|
|
if (project in x): |
|
|
matches.append(x) |
|
|
drop=gr.Dropdown.update(choices=matches) |
|
|
|
|
|
return drop |
|
|
|
|
|
|
|
|
def clear(demo): |
|
|
return None,None,None,None |
|
|
|
|
|
def saveExcel(Dictionary,plan): |
|
|
print('sdjbfkhbf') |
|
|
plan2=str(plan) |
|
|
|
|
|
|
|
|
|
|
|
d=dropbox_upload_file('.',local_file=Dictionary,dropbox_file_path='/savedMeasurements/'+plan2+'summaryXML.xml') |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
with gr.Blocks(css="#search {background: green}") as mainBlock: |
|
|
|
|
|
|
|
|
with gr.Tab("Main UI"): |
|
|
with gr.Row(): |
|
|
|
|
|
with gr.Accordion("User Guide ",open=False): |
|
|
gr.Markdown("Please read this before you use this tool. \n Note : The algorithm is based on detecting shapes from the plan. Some shapes such as tables and textboxes containing information about the plan may be seen as a shape and inserted into the algorithm as well. To avoid this, please clean up the plan before you choose to measure it by erasing them or by drawing a white rectangle above them using any external tool. \n Please note that the pdfs inserted in this tab should be pile caps only.\n \n The tool is divided into two main parts: \n \n * First Part (until the measure button) \n \t - You will find three dropdowns. Choose the name of the project you want to measure, along with the project part, and the project section. \n \t- Then choose whether this project contains levels or not. If you wish to measure all of the plan choose Measure full image. If you wish to measure certain regions of the plan or divide the plan into regions please choose Measure Specific regions. \n \t - If you choose Measure specific regions, please draw shapes around the desired regions on Bluebeam or any external tool before choosing to measure this plan. \n Also, you should insert the colors in rgb format (Red-Green-Blue) of the levels. \n \n The output of the first part will be in the unit pixels. To convert the measurements into a metric unit. Please refer to the the second part for detailed information. \n \n * Second part (Unit Conversion - This occurs once only) \n \t - Choose one of the shapes of the measured plan (preferably the largest shape) and measure it in Bluebeam. \n \t - In the first field labeled Real value, please enter the value you obtained from the measurement you made on Bluebeam. \n \t - In the second field labeled Pixel value, enter the pixel value of the same shape in which you measured that is shown in the output of the first part. \n \t - The unit in which the conversion will be into. \n This creates a ratio so that the conversion would be as accurate as possible. You can think of this as the scale check logic in Bluebeam. \n Outputs:\n \t The first output is an image of the plan measured and color sorted. \n \t The second output is a representation of the Legend exported.\n \t The column named MC-Template Name is empty for you to enter the MC-T name. \n \t The column named Area is the area measured of one of the shape.\n \t The column named Occurences is the number of count of this shape - This is just to make sure every shape was seen correctly and thus summed later correctly.\n \t The column named Total Area contains the summed areas of each shape \n \t The column named Unit refers to the unit in which the conversion was made to.") |
|
|
|
|
|
|
|
|
with gr.Row(): |
|
|
|
|
|
with gr.Column(): |
|
|
project=gr.Dropdown(choices=['BMW job1','BMW job2','Project C'],interactive=True,label='Projects') |
|
|
drop=gr.Dropdown(choices=None,interactive=True,label='project parts') |
|
|
radio_button = gr.Dropdown(choices=['foundation','external','interior'], value=None, interactive=True,label='sections') |
|
|
|
|
|
in2=gr.Radio(label="Measurement",choices=["Measure Full Image", "Measure Specified Regions"]) |
|
|
in3=gr.Radio(label="Area or Perimeter",choices=["Area", "Perimeter"]) |
|
|
with gr.Row(): |
|
|
in4=gr.ColorPicker(label="color" ) |
|
|
in5=gr.ColorPicker(label="color" ) |
|
|
in6=gr.ColorPicker(label="color" ) |
|
|
in7=gr.ColorPicker(label="color" ) |
|
|
in8=gr.ColorPicker(label="color" ) |
|
|
in9=gr.ColorPicker(label="color" ) |
|
|
in10=gr.ColorPicker(label="color" ) |
|
|
in11=gr.ColorPicker(label="color" ) |
|
|
in12=gr.ColorPicker(label="color" ) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
with gr.Column(): |
|
|
img1=gr.Image() |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
show_button = gr.Button(value="Measure",elem_id='search') |
|
|
with gr.Row(): |
|
|
|
|
|
with gr.Column(): |
|
|
num1=gr.Number(label='Real value') |
|
|
num2=gr.Number(label='Pixel value') |
|
|
dp=gr.Dropdown(["m", "cm", "mm"]) |
|
|
btn = gr.Button("Submit Ratio") |
|
|
|
|
|
check=gr.Checkbox(label='SaveOutput') |
|
|
check1=gr.Checkbox(label='Export to Excel') |
|
|
|
|
|
with gr.Column(): |
|
|
out1=gr.Image(label="Image", type="pil", image_mode="RGBA") |
|
|
out2=gr.Dataframe(label='Dictionary', interactive=True) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
buttonSaveDf=gr.Button("Save dataframe") |
|
|
with gr.Tab("Google Sheets Legend"): |
|
|
|
|
|
|
|
|
out3=gr.HTML() |
|
|
btn1=gr.Button('Save updated MC-T Names') |
|
|
|
|
|
|
|
|
show_button.click(fn=getMeasurement, inputs=[drop, check ,check1, dp,in2,in3,in4,in5,in6,in7,in8,in9,in10,in11,in12],outputs=img1) |
|
|
buttonSaveDf.click(fn=saveExcel,inputs=[out2,project]) |
|
|
btn1.click(fn=getdropdownValues,every=20) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
btn.click(fn=getMeasurement, inputs=[drop, check,check1 ,dp,in2,in3,in4,in5,in6,in7,in8,in9,in10,in11,in12,num1,num2],outputs=[out1,out2,out3]) |
|
|
project.change(fn=update_dropdown, inputs=[project], outputs=drop) |
|
|
|
|
|
mainBlock.launch(debug=True,enable_queue=True) |
|
|
|