Source code for yapcad.drawable

## base class of drawable for yapCAD
## Copyright (c) 2020 Richard W. DeVaul
## Copyright (c) 2020 yapCAD contributors
## All rights reserved
## See licensing terms here: https://github.com/rdevaul/yapCAD/blob/master/LICENSE

from yapcad.geom import *
from yapcad.geometry import *

## Generic drawing functions -- assumed to use current coordinate
## transform and drawing pen (color, line weight, etc.)
 
[docs] class Drawable: """Base class for yapCAD drawables""" ## utility functions for drawing ## ----------------------------- ## pure virtual functions -- override for specific rendering ## system
[docs] def draw_arc(self,p,r,start,end): print("pure virtual draw_arc called: {}, {}, {}, {}".format(p,r,start,end)) return
[docs] def draw_ellipse(self, center, semi_major, semi_minor, rotation, start, end): """Draw an ellipse or elliptical arc. Parameters ---------- center : point Center point of the ellipse. semi_major : float Semi-major axis length. semi_minor : float Semi-minor axis length. rotation : float Rotation of major axis from x-axis in degrees. start : float Start angle in degrees. end : float End angle in degrees. """ print("pure virtual draw_ellipse called: {}, {}, {}, {}, {}, {}".format( center, semi_major, semi_minor, rotation, start, end)) return
[docs] def draw_line(self,p1,p2): print("pure virtual draw_line called: {}, {}".format(p1,p2)) return
[docs] def draw_text(self,text,location, align='left', attr={}): print("pure virtual draw_text called: {}, {}, {}, {}".format(text,location,align,attr)) return
## non-virtual utility drawing functions
[docs] def draw_circle(self,p,r): self.draw_arc(p,r,0.0,360.0) return
## utility function to draw an "x", centered on point p inside square of ## dimension d
[docs] def draw_x(self,p,d): hd=d/2 p1=add(p,vect([-hd,-hd,0])) p2=add(p,vect([hd,hd,0])) p3=add(p,vect([-hd,hd,0])) p4=add(p,vect([hd,-hd,0])) self.draw_line(p1,p2) self.draw_line(p3,p4) return;
## utiitly function to draw a point based on the current point style
[docs] def draw_point(self,p): if 'x' in self.__pointstyle: self.draw_x(p,self.__pointsize*2) if 'o' in self.__pointstyle: self.draw_circle(p,self.__pointsize)
## utility function to draw a 2D or 3D bounding box
[docs] def draw_bbox(self,box,dim3=False): length = box[1][0]-box[0][0] width = box[1][1]-box[0][1] height = box[1][2]-box[0][2] p0=box[0] p1=add(p0,point(length,0,0)) p2=add(p1,point(0,width,0)) p3=add(p0,point(0,width,0)) self.draw_line(p0,p1) self.draw_line(p1,p2) self.draw_line(p2,p3) self.draw_line(p3,p0) if not dim3: return p4=add(p0,point(0,0,height)) p5=add(p4,point(length,0,0)) p6=box[1] p7=add(p4,point(0,width,0)) self.draw_line(p4,p5) self.draw_line(p5,p6) self.draw_line(p6,p7) self.draw_line(p7,p4) self.draw_line(p0,p4) self.draw_line(p1,p5) self.draw_line(p2,p6) self.draw_line(p3,p7)
def __init__(self): self.__pointstyle = 'xo' self.__pointsize = 0.1 self.__linetype = False self.__linewidth = 0.1 self.__linecolor = False self.__fillcolor = False self.__polystyle = 'lines' self.__layer = False self.__layerlist = [ False, 'default' ] ## Various property functions @property def layerlist(self): return self.__layerlist def _set_layerlist(self,lst): self.__layerlist = lst @layerlist.setter def layerlist(self,lst): if isinstance(lst,list): self._set_layerlist(lst) else: raise ValueError('bad layer list ' + str(lst)) @property def layer(self): return self.__layer def _set_layer(self,lyr): self.__layer = lyr @layer.setter def layer(self,lyr=False): if lyr in self.layerlist: self._set_layer(lyr) else: raise ValueError('bad layer: ' + str(lyr)) @property def polystyle(self): return self.__polystyle def _set_polystyle(self,pst): self.__polystyle = pst @polystyle.setter def polystyle(self,pst=False): if pst in ['points','lines','both']: self._set_polystyle(pst) else: raise ValueError('bad polystyle') @property def pointstyle(self): return self.__pointstyle def _set_pointstyle(self,pst): self.__pointstyle=pst @pointstyle.setter def pointstyle(self,pst=False): if pst in [False, 'x','o','xo']: self._set_pointstyle(pst) else: raise ValueError('bad pointstyle: ' + str(pst)) @property def pointsize(self): return self.__pointsize def _set_pointsize(self,ps): self.__pointsize=ps @pointsize.setter def pointsize(self,ps=False): if not isinstance(ps,(int,float)): raise ValueError('invalid pointsize ' + str(ps)) if isinstance(ps,bool) and ps == False: self._set_pointsize(0.1) elif ps < epsilon: ps = epsilon self._set_pointsize(ps) @property def linewidth(self): return self.__linewidth def _set_linewidth(self,lw): self.__linewidth=lw @linewidth.setter def linewidth(self,lw=False): if not isinstance(lw,(int,float)): raise ValueError('invalid pointsize ' + str(lw)) if isinstance(lw,bool) and lw ==False: lw = 0.1 elif lw < epsilon: lw = epsilon self._set_linewidth(lw) @property def linetype(self): return self.__linetype def _set_linetype(self,lt): self.__linetype = lt @linetype.setter def linetype(self,lt=False): if lt in [ False, 'Continuous' ]: # only continuous linetype supported in base class self._set_linetype(False) else: raise ValueError('unsupported linetype ' + str(lt)) ## color is a complex property -- it can be set as an AUTOCAD ## index color, a standard color name, or an RGB tripple def __checkcolor(self,c): def isbyte(x): return isinstance(x,int) and x >= 0 and x <= 255 if isinstance(c,bool) and c == False: return True elif (isinstance(c,list) and len(c) == 3 \ and isbyte(c[0]) and isbyte(c[1]) and isbyte(c[2])) or \ (isinstance(c,int) and c >= 0 and c < len(self.colormapAUTOCAD)) or\ isinstance(c,str) and c in self.colordict: return True return False ## line color @property def linecolor(self): return self.__linecolor def _set_linecolor(self,c): self.__linecolor=c @linecolor.setter def linecolor(self,c=False): if self.__checkcolor(c): self._set_linecolor(c) else: raise ValueError('bad linecolor ' + str(c)) ## fill color @property def fillcolor(self): return self.__fillcolor def _set_fillcolor(self,c): self.__fillcolor = c @fillcolor.setter def fillcolor(self,c=False): if self.__checkcolor(c): self._set_fillcolor(c) else: raise ValueError('bad fillcolor ' + str(c)) ## non-property methods def __repr__(self): return 'an abstract Drawable instance'
[docs] def str(self): return self.__repr__()
[docs] def print(self): print(self.str())
[docs] def draw(self,x): if ispoint(x): self.draw_point(x) elif isline(x): self.draw_line(x[0],x[1]) elif isarc(x): self.draw_arc(x[0],x[1][0],x[1][1],x[1][2]) elif isellipse(x): meta = x[2] self.draw_ellipse(x[1], meta['semi_major'], meta['semi_minor'], meta['rotation'], meta['start'], meta['end']) elif ispoly(x): if self.polystyle in ('points','lines','both'): if self.polystyle == 'points' or \ self.polystyle == 'both': for e in x: self.draw(e) if self.polystyle == 'lines' or \ self.polystyle == 'both': for i in range(1,len(x)): self.draw(line(x[i-1],x[i])) else: raise ValueError("bad value for polystyle: {}".format(self.polystyle)) elif iscatmullrom(x): from yapcad.spline import sample_catmullrom pts = sample_catmullrom(x) closed = bool(x[2].get('closed', False)) for i in range(1, len(pts)): self.draw_line(pts[i-1], pts[i]) if closed and pts: self.draw_line(pts[-1], pts[0]) elif isnurbs(x): from yapcad.spline import sample_nurbs meta = x[2] default = max(32, len(x[1]) * 8) count = int(meta.get('samples', default)) pts = sample_nurbs(x, samples=max(4, count)) for i in range(1, len(pts)): self.draw_line(pts[i-1], pts[i]) elif isinstance(x,Geometry): gl = x.geom self.draw(gl) elif isinstance(x,list): # could be a geometry list, or a list # that mixes yapcad.geom elements and yapcad.geometry # Geeometry instances. If the list contains an # inappropriate element it will be caught in the "else" case below. for e in x: self.draw(e) else: raise ValueError(f'bad argument to Drawable.draw(): {x}')
## cause drawing page to be rendered -- pure virtual in base class
[docs] def display(self): print('pure virtual display function called') return True
## Standard color names per W3C CSS Color Module Level 4 keywords. # Standardized color keywords (CSS Color Module Level 4) plus # X11 gray/grey ramp entries for broader palette coverage. colordict= { 'aliceblue': ([240, 248, 255], None), 'antiquewhite': ([250, 235, 215], None), 'aqua': ([0, 255, 255], 4), 'aquamarine': ([127, 255, 212], None), 'azure': ([240, 255, 255], None), 'beige': ([245, 245, 220], None), 'bisque': ([255, 228, 196], None), 'black': ([0, 0, 0], 0), 'blanchedalmond': ([255, 235, 205], None), 'blue': ([0, 0, 255], 5), 'blueviolet': ([138, 43, 226], None), 'brown': ([165, 42, 42], None), 'burlywood': ([222, 184, 135], None), 'cadetblue': ([95, 158, 160], None), 'chartreuse': ([127, 255, 0], None), 'chocolate': ([210, 105, 30], None), 'coral': ([255, 127, 80], None), 'cornflowerblue': ([100, 149, 237], None), 'cornsilk': ([255, 248, 220], None), 'crimson': ([220, 20, 60], None), 'cyan': ([0, 255, 255], None), 'darkblue': ([0, 0, 139], None), 'darkcyan': ([0, 139, 139], None), 'darkgoldenrod': ([184, 134, 11], None), 'darkgray': ([169, 169, 169], None), 'darkgreen': ([0, 100, 0], None), 'darkgrey': ([169, 169, 169], None), 'darkkhaki': ([189, 183, 107], None), 'darkmagenta': ([139, 0, 139], None), 'darkolivegreen': ([85, 107, 47], None), 'darkorange': ([255, 140, 0], None), 'darkorchid': ([153, 50, 204], None), 'darkred': ([139, 0, 0], None), 'darksalmon': ([233, 150, 122], None), 'darkseagreen': ([143, 188, 143], None), 'darkslateblue': ([72, 61, 139], None), 'darkslategray': ([47, 79, 79], None), 'darkslategrey': ([47, 79, 79], None), 'darkturquoise': ([0, 206, 209], None), 'darkviolet': ([148, 0, 211], None), 'deeppink': ([255, 20, 147], None), 'deepskyblue': ([0, 191, 255], None), 'dimgray': ([105, 105, 105], None), 'dimgrey': ([105, 105, 105], None), 'dodgerblue': ([30, 144, 255], None), 'firebrick': ([178, 34, 34], None), 'floralwhite': ([255, 250, 240], None), 'forestgreen': ([34, 139, 34], None), 'fuchsia': ([255, 0, 255], 6), 'gainsboro': ([220, 220, 220], None), 'ghostwhite': ([248, 248, 255], None), 'gold': ([255, 215, 0], None), 'goldenrod': ([218, 165, 32], None), 'gray': ([128, 128, 128], 8), 'gray0': ([0, 0, 0], None), 'gray1': ([3, 3, 3], None), 'gray10': ([26, 26, 26], None), 'gray100': ([255, 255, 255], None), 'gray11': ([28, 28, 28], None), 'gray12': ([31, 31, 31], None), 'gray13': ([33, 33, 33], None), 'gray14': ([36, 36, 36], None), 'gray15': ([38, 38, 38], None), 'gray16': ([41, 41, 41], None), 'gray17': ([43, 43, 43], None), 'gray18': ([46, 46, 46], None), 'gray19': ([48, 48, 48], None), 'gray2': ([5, 5, 5], None), 'gray20': ([51, 51, 51], None), 'gray21': ([54, 54, 54], None), 'gray22': ([56, 56, 56], None), 'gray23': ([59, 59, 59], None), 'gray24': ([61, 61, 61], None), 'gray25': ([64, 64, 64], None), 'gray26': ([66, 66, 66], None), 'gray27': ([69, 69, 69], None), 'gray28': ([71, 71, 71], None), 'gray29': ([74, 74, 74], None), 'gray3': ([8, 8, 8], None), 'gray30': ([76, 76, 76], None), 'gray31': ([79, 79, 79], None), 'gray32': ([82, 82, 82], None), 'gray33': ([84, 84, 84], None), 'gray34': ([87, 87, 87], None), 'gray35': ([89, 89, 89], None), 'gray36': ([92, 92, 92], None), 'gray37': ([94, 94, 94], None), 'gray38': ([97, 97, 97], None), 'gray39': ([99, 99, 99], None), 'gray4': ([10, 10, 10], None), 'gray40': ([102, 102, 102], None), 'gray41': ([105, 105, 105], None), 'gray42': ([107, 107, 107], None), 'gray43': ([110, 110, 110], None), 'gray44': ([112, 112, 112], None), 'gray45': ([115, 115, 115], None), 'gray46': ([117, 117, 117], None), 'gray47': ([120, 120, 120], None), 'gray48': ([122, 122, 122], None), 'gray49': ([125, 125, 125], None), 'gray5': ([13, 13, 13], None), 'gray50': ([128, 128, 128], None), 'gray51': ([130, 130, 130], None), 'gray52': ([133, 133, 133], None), 'gray53': ([135, 135, 135], None), 'gray54': ([138, 138, 138], None), 'gray55': ([140, 140, 140], None), 'gray56': ([143, 143, 143], None), 'gray57': ([145, 145, 145], None), 'gray58': ([148, 148, 148], None), 'gray59': ([150, 150, 150], None), 'gray6': ([15, 15, 15], None), 'gray60': ([153, 153, 153], None), 'gray61': ([156, 156, 156], None), 'gray62': ([158, 158, 158], None), 'gray63': ([161, 161, 161], None), 'gray64': ([163, 163, 163], None), 'gray65': ([166, 166, 166], None), 'gray66': ([168, 168, 168], None), 'gray67': ([171, 171, 171], None), 'gray68': ([173, 173, 173], None), 'gray69': ([176, 176, 176], None), 'gray7': ([18, 18, 18], None), 'gray70': ([178, 178, 178], None), 'gray71': ([181, 181, 181], None), 'gray72': ([184, 184, 184], None), 'gray73': ([186, 186, 186], None), 'gray74': ([189, 189, 189], None), 'gray75': ([191, 191, 191], None), 'gray76': ([194, 194, 194], None), 'gray77': ([196, 196, 196], None), 'gray78': ([199, 199, 199], None), 'gray79': ([201, 201, 201], None), 'gray8': ([20, 20, 20], None), 'gray80': ([204, 204, 204], None), 'gray81': ([207, 207, 207], None), 'gray82': ([209, 209, 209], None), 'gray83': ([212, 212, 212], None), 'gray84': ([214, 214, 214], None), 'gray85': ([217, 217, 217], None), 'gray86': ([219, 219, 219], None), 'gray87': ([222, 222, 222], None), 'gray88': ([224, 224, 224], None), 'gray89': ([227, 227, 227], None), 'gray9': ([23, 23, 23], None), 'gray90': ([230, 230, 230], None), 'gray91': ([232, 232, 232], None), 'gray92': ([235, 235, 235], None), 'gray93': ([237, 237, 237], None), 'gray94': ([240, 240, 240], None), 'gray95': ([242, 242, 242], None), 'gray96': ([245, 245, 245], None), 'gray97': ([247, 247, 247], None), 'gray98': ([250, 250, 250], None), 'gray99': ([252, 252, 252], None), 'green': ([0, 127, 0], 94), 'greenyellow': ([173, 255, 47], None), 'grey': ([128, 128, 128], None), 'grey0': ([0, 0, 0], None), 'grey1': ([3, 3, 3], None), 'grey10': ([26, 26, 26], None), 'grey100': ([255, 255, 255], None), 'grey11': ([28, 28, 28], None), 'grey12': ([31, 31, 31], None), 'grey13': ([33, 33, 33], None), 'grey14': ([36, 36, 36], None), 'grey15': ([38, 38, 38], None), 'grey16': ([41, 41, 41], None), 'grey17': ([43, 43, 43], None), 'grey18': ([46, 46, 46], None), 'grey19': ([48, 48, 48], None), 'grey2': ([5, 5, 5], None), 'grey20': ([51, 51, 51], None), 'grey21': ([54, 54, 54], None), 'grey22': ([56, 56, 56], None), 'grey23': ([59, 59, 59], None), 'grey24': ([61, 61, 61], None), 'grey25': ([64, 64, 64], None), 'grey26': ([66, 66, 66], None), 'grey27': ([69, 69, 69], None), 'grey28': ([71, 71, 71], None), 'grey29': ([74, 74, 74], None), 'grey3': ([8, 8, 8], None), 'grey30': ([76, 76, 76], None), 'grey31': ([79, 79, 79], None), 'grey32': ([82, 82, 82], None), 'grey33': ([84, 84, 84], None), 'grey34': ([87, 87, 87], None), 'grey35': ([89, 89, 89], None), 'grey36': ([92, 92, 92], None), 'grey37': ([94, 94, 94], None), 'grey38': ([97, 97, 97], None), 'grey39': ([99, 99, 99], None), 'grey4': ([10, 10, 10], None), 'grey40': ([102, 102, 102], None), 'grey41': ([105, 105, 105], None), 'grey42': ([107, 107, 107], None), 'grey43': ([110, 110, 110], None), 'grey44': ([112, 112, 112], None), 'grey45': ([115, 115, 115], None), 'grey46': ([117, 117, 117], None), 'grey47': ([120, 120, 120], None), 'grey48': ([122, 122, 122], None), 'grey49': ([125, 125, 125], None), 'grey5': ([13, 13, 13], None), 'grey50': ([128, 128, 128], None), 'grey51': ([130, 130, 130], None), 'grey52': ([133, 133, 133], None), 'grey53': ([135, 135, 135], None), 'grey54': ([138, 138, 138], None), 'grey55': ([140, 140, 140], None), 'grey56': ([143, 143, 143], None), 'grey57': ([145, 145, 145], None), 'grey58': ([148, 148, 148], None), 'grey59': ([150, 150, 150], None), 'grey6': ([15, 15, 15], None), 'grey60': ([153, 153, 153], None), 'grey61': ([156, 156, 156], None), 'grey62': ([158, 158, 158], None), 'grey63': ([161, 161, 161], None), 'grey64': ([163, 163, 163], None), 'grey65': ([166, 166, 166], None), 'grey66': ([168, 168, 168], None), 'grey67': ([171, 171, 171], None), 'grey68': ([173, 173, 173], None), 'grey69': ([176, 176, 176], None), 'grey7': ([18, 18, 18], None), 'grey70': ([178, 178, 178], None), 'grey71': ([181, 181, 181], None), 'grey72': ([184, 184, 184], None), 'grey73': ([186, 186, 186], None), 'grey74': ([189, 189, 189], None), 'grey75': ([191, 191, 191], None), 'grey76': ([194, 194, 194], None), 'grey77': ([196, 196, 196], None), 'grey78': ([199, 199, 199], None), 'grey79': ([201, 201, 201], None), 'grey8': ([20, 20, 20], None), 'grey80': ([204, 204, 204], None), 'grey81': ([207, 207, 207], None), 'grey82': ([209, 209, 209], None), 'grey83': ([212, 212, 212], None), 'grey84': ([214, 214, 214], None), 'grey85': ([217, 217, 217], None), 'grey86': ([219, 219, 219], None), 'grey87': ([222, 222, 222], None), 'grey88': ([224, 224, 224], None), 'grey89': ([227, 227, 227], None), 'grey9': ([23, 23, 23], None), 'grey90': ([230, 230, 230], None), 'grey91': ([232, 232, 232], None), 'grey92': ([235, 235, 235], None), 'grey93': ([237, 237, 237], None), 'grey94': ([240, 240, 240], None), 'grey95': ([242, 242, 242], None), 'grey96': ([245, 245, 245], None), 'grey97': ([247, 247, 247], None), 'grey98': ([250, 250, 250], None), 'grey99': ([252, 252, 252], None), 'honeydew': ([240, 255, 240], None), 'hotpink': ([255, 105, 180], None), 'indianred': ([205, 92, 92], None), 'indigo': ([75, 0, 130], None), 'ivory': ([255, 255, 240], None), 'khaki': ([240, 230, 140], None), 'lavender': ([230, 230, 250], None), 'lavenderblush': ([255, 240, 245], None), 'lawngreen': ([124, 252, 0], None), 'lemonchiffon': ([255, 250, 205], None), 'lightblue': ([173, 216, 230], None), 'lightcoral': ([240, 128, 128], None), 'lightcyan': ([224, 255, 255], None), 'lightgoldenrodyellow': ([250, 250, 210], None), 'lightgray': ([211, 211, 211], None), 'lightgreen': ([144, 238, 144], None), 'lightgrey': ([211, 211, 211], None), 'lightpink': ([255, 182, 193], None), 'lightsalmon': ([255, 160, 122], None), 'lightseagreen': ([32, 178, 170], None), 'lightskyblue': ([135, 206, 250], None), 'lightslategray': ([119, 136, 153], None), 'lightslategrey': ([119, 136, 153], None), 'lightsteelblue': ([176, 196, 222], None), 'lightyellow': ([255, 255, 224], None), 'lime': ([0, 255, 0], 3), 'limegreen': ([50, 205, 50], None), 'linen': ([250, 240, 230], None), 'magenta': ([255, 0, 255], None), 'maroon': ([127, 0, 0], 14), 'mediumaquamarine': ([102, 205, 170], None), 'mediumblue': ([0, 0, 205], None), 'mediumorchid': ([186, 85, 211], None), 'mediumpurple': ([147, 112, 219], None), 'mediumseagreen': ([60, 179, 113], None), 'mediumslateblue': ([123, 104, 238], None), 'mediumspringgreen': ([0, 250, 154], None), 'mediumturquoise': ([72, 209, 204], None), 'mediumvioletred': ([199, 21, 133], None), 'midnightblue': ([25, 25, 112], None), 'mintcream': ([245, 255, 250], None), 'mistyrose': ([255, 228, 225], None), 'moccasin': ([255, 228, 181], None), 'navajowhite': ([255, 222, 173], None), 'navy': ([0, 0, 128], 174), 'oldlace': ([253, 245, 230], None), 'olive': ([127, 127, 0], 54), 'olivedrab': ([107, 142, 35], None), 'orange': ([255, 165, 0], None), 'orangered': ([255, 69, 0], None), 'orchid': ([218, 112, 214], None), 'palegoldenrod': ([238, 232, 170], None), 'palegreen': ([152, 251, 152], None), 'paleturquoise': ([175, 238, 238], None), 'palevioletred': ([219, 112, 147], None), 'papayawhip': ([255, 239, 213], None), 'peachpuff': ([255, 218, 185], None), 'peru': ([205, 133, 63], None), 'pink': ([255, 192, 203], None), 'plum': ([221, 160, 221], None), 'powderblue': ([176, 224, 230], None), 'purple': ([128, 0, 128], 214), 'rebeccapurple': ([102, 51, 153], None), 'red': ([255, 0, 0], 1), 'rosybrown': ([188, 143, 143], None), 'royalblue': ([65, 105, 225], None), 'saddlebrown': ([139, 69, 19], None), 'salmon': ([250, 128, 114], None), 'sandybrown': ([244, 164, 96], None), 'seagreen': ([46, 139, 87], None), 'seashell': ([255, 245, 238], None), 'sienna': ([160, 82, 45], None), 'silver': ([192, 192, 192], 9), 'skyblue': ([135, 206, 235], None), 'slateblue': ([106, 90, 205], None), 'slategray': ([112, 128, 144], None), 'slategrey': ([112, 128, 144], None), 'snow': ([255, 250, 250], None), 'springgreen': ([0, 255, 127], None), 'steelblue': ([70, 130, 180], None), 'tan': ([210, 180, 140], None), 'teal': ([0, 127, 127], 134), 'thistle': ([216, 191, 216], None), 'tomato': ([255, 99, 71], None), 'turquoise': ([64, 224, 208], None), 'violet': ([238, 130, 238], None), 'wheat': ([245, 222, 179], None), 'white': ([255, 255, 255], 7), 'whitesmoke': ([245, 245, 245], None), 'yellow': ([255, 255, 0], 2), 'yellowgreen': ([154, 205, 50], None), } ## AUTOCAD color index: ## https://forums.autodesk.com/t5/visual-lisp-autolisp-and-general/ ## rgb-values-of-the-256-standard-indexed-colors/td-p/848912 colormapAUTOCAD = [ [0,0,0], [255,0,0], [255,255,0], [0,255,0], [0,255,255], [0,0,255], [255,0,255], [255,255,255], [128,128,128], [192,192,192], [255,0,0], [255,127,127], [165,0,0], [165,82,82], [127,0,0], [127,63,63], [76,0,0], [76,38,38], [38,0,0], [38,19,19], [255,63,0], [255,159,127], [165,41,0], [165,103,82], [127,31,0], [127,79,63], [76,19,0], [76,47,38], [38,9,0], [38,23,19], [255,127,0], [255,191,127], [168,82,0], [165,124,82], [127,63,0], [127,95,63], [76,38,0], [76,57,38], [38,19,0], [38,28,19], [255,191,0], [255,223,127], [165,124,0], [165,145,82], [127,95,0], [127,111,63], [76,57,0], [76,66,38], [38,28,0], [38,33,19], [255,255,0], [255,255,127], [165,165,0], [165,165,82], [127,127,0], [127,127,63], [76,76,0], [76,76,38], [38,38,0], [38,38,19], [191,255,0], [223,255,127], [124,165,0], [145,165,82], [95,127,0], [111,127,63], [57,76,0], [66,76,38], [28,38,0], [33,38,19], [127,255,0], [191,255,127], [82,165,0], [124,165,82], [63,127,0], [95,127,63], [38,76,0], [57,76,38], [19,38,0], [28,38,19], [63,255,0], [159,255,127], [41,165,0], [103,165,82], [31,127,0], [79,127,63], [19,76,0], [47,76,38], [9,38,0], [23,38,19], [0,255,0], [127,255,127], [0,165,0], [82,165,82], [0,127,0], [63,127,63], [0,76,0], [38,76,38], [0,38,0], [19,38,19], [0,255,63], [127,255,159], [0,165,41], [82,165,103], [0,127,31], [63,127,79], [0,76,19], [38,76,47], [0,38,9], [19,38,23], [0,255,127], [127,255,191], [0,165,82], [82,165,124], [0,127,63], [63,127,95], [0,76,38], [38,76,57], [0,38,19], [19,38,28], [0,255,191], [127,255,223], [0,165,124], [82,165,145], [0,127,95], [63,127,111], [0,76,57], [38,76,66], [0,38,28], [19,38,33], [0,255,255], [127,255,255], [0,165,165], [82,165,165], [0,127,127], [63,127,127], [0,76,76], [38,76,76], [0,38,38], [19,38,38], [0,191,255], [127,223,255], [0,124,165], [82,145,165], [0,95,127], [63,111,127], [0,57,76], [38,66,76], [0,28,38], [19,33,38], [0,127,255], [127,191,255], [0,82,165], [82,124,165], [0,63,127], [63,95,127], [0,38,76], [38,57,76], [0,19,38], [19,28,38], [0,63,255], [127,159,255], [0,41,165], [82,103,165], [0,31,127], [63,79,127], [0,19,76], [38,47,76], [0,9,38], [19,23,38], [0,0,255], [127,127,255], [0,0,165], [82,82,165], [0,0,127], [63,63,127], [0,0,76], [38,38,76], [0,0,38], [19,19,38], [63,0,255], [159,127,255], [41,0,165], [103,82,165], [31,0,127], [79,63,127], [19,0,76], [47,38,76], [9,0,38], [23,19,38], [127,0,255], [191,127,255], [82,0,165], [124,82,165], [63,0,127], [95,63,127], [38,0,76], [57,38,76], [19,0,38], [28,19,38], [191,0,255], [223,127,255], [124,0,165], [145,82,165], [95,0,127], [111,63,127], [57,0,76], [66,38,76], [28,0,38], [33,19,38], [255,0,255], [255,127,255], [165,0,165], [165,82,165], [127,0,127], [127,63,127], [76,0,76], [76,38,76], [38,0,38], [38,19,38], [255,0,191], [255,127,223], [165,0,124], [165,82,145], [127,0,95], [127,63,111], [76,0,57], [76,38,66], [38,0,28], [38,19,33], [255,0,127], [255,127,191], [165,0,82], [165,82,124], [127,0,63], [127,63,95], [76,0,38], [76,38,57], [38,0,19], [38,19,28], [255,0,63], [255,127,159], [165,0,41], [165,82,103], [127,0,31], [127,63,79], [76,0,19], [76,38,47], [38,0,9], [38,19,23], [0,0,0], [45,45,45], [91,91,91], [137,137,137], [183,183,183], [179,179,179], False # bylaer ] ## function to convert between different color representations
[docs] def thing2color(self,thing,convert='b',colormap=None,colordict=None): def _b2f(c): return [c[0] / 255.0, c[1] / 255.0, c[2] / 255.0] def _f2b(c): return [round(c[0] * 255.0), round(c[1] * 255.0), round(c[2] * 255.0)] def _nearest_index(rgb): best_idx = 0 best_dist = float('inf') for idx, candidate in enumerate(colormap): if not isinstance(candidate, (list, tuple)) or len(candidate) != 3: continue dist = ((candidate[0] - rgb[0]) ** 2 + (candidate[1] - rgb[1]) ** 2 + (candidate[2] - rgb[2]) ** 2) if dist < best_dist: best_idx = idx best_dist = dist if dist == 0: break return best_idx def _b2i(c): for i in range(len(colormap)): if colormap[i] == c: return i return _nearest_index(c) def _f2i(c): return _b2i(_f2b(c)) def _isgoodf(x): return isinstance(x,float) and x >= 0.0 and x <= 1.0 def _isgoodb(x): return isinstance(x,int) and x >= 0 and x < 256 def _isgoodfc(c): return isinstance(c,(list,tuple)) and len(c) == 3 and\ _isgoodf(c[0]) and _isgoodf(c[1]) and _isgoodf(c[2]) def _isgoodbc(c): return isinstance(c,(list,tuple)) and len(c) == 3 and\ _isgoodb(c[0]) and _isgoodb(c[1]) and _isgoodb(c[2]) if colormap == None: colormap = self.colormapAUTOCAD if colordict == None: colordict = self.colordict if convert not in ['f','b','i']: raise ValueError('bad colormap conversion') c = False if _isgoodfc(thing): if convert == 'b': return _f2b(thing) elif convert == 'i': return _f2i(thing) else: return thing elif _isgoodbc(thing): if convert == 'i': return _b2i(thing) if convert == 'f': return _b2f(thing) else: return thing elif isinstance(thing,str): key = thing.lower() if key not in colordict: raise ValueError('bad color name passed to thing2color: {}'.format(thing)) cd = colordict[key] if isinstance(cd,bool) and cd == False: raise ValueError('bad color name passed to thing2color: {}'.format(thing)) if convert == 'i': idx = cd[1] if idx is None: idx = _nearest_index(cd[0]) return idx else: c = list(cd[0]) elif isinstance(thing,int): if thing < 0 or thing > len(colormap): raise ValueError('colormap index out of range: {}'.format(thing)) if convert == 'i': return thing else: c = colormap[thing] else: raise ValueError('bad thing passed to thing2color: {}'.format(thing)) if isinstance(c,bool) and c == False: return False if convert == 'i': return _b2i(c) elif convert == 'f': return _b2f(c) return list(c)