def surface_normal(self, ray, acute=True): """ Returns surface normal in point where ray hits CSGint surface """ """ Ensure surface_point on CSGint surface """ invtransform = tf.inverse_matrix(self.transform) localray = Ray() localray.position = transform_point(ray.position, invtransform) localray.direction = transform_direction(ray.direction, invtransform) bool1 = self.INTone.on_surface(localray.position) bool2 = self.INTtwo.on_surface(localray.position) assertbool = False if bool1 == True and self.INTtwo.contains(localray.position) == True: assertbool = True if bool2 == True and self.INTone.contains(localray.position) == True: assertbool = True if bool1 == bool2 == True: assertbool = True assert assertbool == True if bool1 == True: return self.INTone.surface_normal(ray, acute) else: return self.INTtwo.surface_normal(ray, acute)
def surface_normal(self, ray, acute=True): """ Return the surface normal for a ray arriving on the CSGsub surface. """ invtransform = tf.inverse_matrix(self.transform) localray = Ray() localray.position = transform_point(ray.position, invtransform) localray.direction = transform_direction(ray.direction, invtransform) bool1 = self.SUBplus.on_surface(localray.position) bool2 = self.SUBminus.on_surface(localray.position) assertbool = False if bool1 == True and self.SUBminus.contains(localray.position) == False: assertbool = True if bool2 == True and self.SUBplus.contains(localray.position) == True: assertbool = True assert assertbool == True if bool1 == True and self.SUBminus.contains(localray.position) == False: return self.SUBplus.surface_normal(ray, acute) if bool2 == True and self.SUBplus.contains(localray.position) == True: if acute: return self.SUBminus.surface_normal(ray,acute) else: normal = -1 * self.SUBminus.surface_normal(ray, acute=True) # Remove signed zeros for i in range(0,3): if normal[i] == 0.0: normal[i] = 0.0 return normal
def shade(hitpoint, hitobj, ray, objectlist, lightlist): """calculates the final color at the given hitpoint. recursive-depth is given by CONSTANT:max_level""" objcolor = hitobj.material.baseColorAt(hitpoint) amb_color = objcolor.scale(hitobj.material.amb) n = hitobj.normalAt(hitpoint) color = amb_color # fuer jede lichtquelle for light in lightlist: lightdir = light - hitpoint l = lightdir.normalized() shadowray = Ray(hitpoint, lightdir) shadow = False # fuer jedes objekt for object in objectlist: hitdist = object.intersectionParameter(shadowray) if hitdist and hitdist > 0: shadow = False difuse_factor = n.dot(l) if difuse_factor < 0: # diffuse nicht dunkler als schatten difuse_factor = 0 lr = (l.scale(-1) - n.scale((2 * l.scale(-1).dot(n)))).normalized() specular_factor = lr.dot(ray.direction.scale(-1)) # specular anteil if specular_factor < 0: specular_factor = 0 dif_color = objcolor.scale(hitobj.material.dif * difuse_factor) #diffuse anteil spec_color = objcolor.scale(hitobj.material.spec * specular_factor**18) #specular anteil if shadow == False: color += dif_color + spec_color ref_factor = hitobj.material.ref if ref_factor and ray.level <= max_level: dr = (ray.direction - n.scale( (2 * ray.direction.dot(n)))).normalized() # spiegleung reflectionray = Ray(hitpoint, dr, ray.level + 1) # ray.level gibt rekursionstiefe des ray an reflectedcolor = traceRay(reflectionray, objectlist, lightlist) color = color.scale(1 - ref_factor) + reflectedcolor.scale(ref_factor) return color
def calcRay(self, x, y): """ Calculates a ray depending on its camera parameters and x and y pixels. """ y = self.hres - y pixelWidth = self.width / (self.wres - 1) pixelHeight = self.height / (self.hres - 1) xcomp = self.s.scale(x * pixelWidth - self.width / 2) ycomp = self.u.scale(y * pixelHeight - self.height / 2) ray = Ray(self.position, self.f + xcomp + ycomp) # e v t l . mehrere S t r a h l e n pro P i x e l return ray
def intersection(self, ray): """ Returns the intersection points of ray with CSGadd in global frame """ # We will need the invtransform later when we return the results..." invtransform = tf.inverse_matrix(self.transform) localray = Ray() localray.position = transform_point(ray.position, invtransform) localray.direction = transform_direction(ray.direction, invtransform) ADDone__intersections = self.ADDone.intersection(localray) ADDtwo__intersections = self.ADDtwo.intersection(localray) """ Cover the simpler cases """ if ADDone__intersections == None and ADDtwo__intersections == None: return None """ Change ..._intersections into tuples """ if ADDone__intersections != None: for i in range(0,len(ADDone__intersections)): point = ADDone__intersections[i] new_point = (point[0], point[1], point[2]) ADDone__intersections[i] = new_point if ADDtwo__intersections != None: for i in range(0,len(ADDtwo__intersections)): point = ADDtwo__intersections[i] new_point = (point[0],point[1],point[2]) ADDtwo__intersections[i] = new_point """ Only intersection points NOT containted in resp. other structure relevant """ ADDone_intersections = [] ADDtwo_intersections = [] if ADDone__intersections != None: for i in range(0,len(ADDone__intersections)): if self.ADDtwo.contains(ADDone__intersections[i]) == False: ADDone_intersections.append(ADDone__intersections[i]) if ADDtwo__intersections != None: for j in range(0,len(ADDtwo__intersections)): if self.ADDone.contains(ADDtwo__intersections[j]) == False: ADDtwo_intersections.append(ADDtwo__intersections[j]) """ => Convert to list """ ADDone_set = set(ADDone_intersections[:]) ADDtwo_set = set(ADDtwo_intersections[:]) combined_set = ADDone_set | ADDtwo_set combined_intersections = list(combined_set) """ Just in case... """ if len(combined_intersections) == 0: return None """ Sort by separation from ray origin """ intersection_separations = [] for point in combined_intersections: intersection_separations.append(separation(ray.position, point)) """ Convert into Numpy arrays in order to sort """ intersection_separations = np.array(intersection_separations) sorted_indices = intersection_separations.argsort() sorted_combined_intersections = [] for index in sorted_indices: sorted_combined_intersections.append(np.array(combined_intersections[index])) global_frame_intersections = [] for point in sorted_combined_intersections: global_frame_intersections.append(transform_point(point, self.transform)) global_frame_intersections_cleared = [] for point in global_frame_intersections: if self.on_surface(point) == True: """ This is only necessary if the two objects have an entire surface region in common, for example consider two boxes joined at one face. """ global_frame_intersections_cleared.append(point) if len(global_frame_intersections_cleared) == 0: return None return global_frame_intersections_cleared
def intersection(self, ray): """ Returns the intersection points of ray with CSGint in global frame """ # We will need the invtransform later when we return the results..." invtransform = tf.inverse_matrix(self.transform) localray = Ray() localray.position = transform_point(ray.position, invtransform) localray.direction = transform_direction(ray.direction, invtransform) INTone__intersections = self.INTone.intersection(localray) INTtwo__intersections = self.INTtwo.intersection(localray) """ Cover the simpler cases """ if INTone__intersections == None and INTtwo__intersections == None: return None """ Change ..._intersections into tuples """ if INTone__intersections != None: for i in range(0,len(INTone__intersections)): point = INTone__intersections[i] new_point = (point[0], point[1], point[2]) INTone__intersections[i] = new_point if INTtwo__intersections != None: for i in range(0,len(INTtwo__intersections)): point = INTtwo__intersections[i] new_point = (point[0], point[1], point[2]) INTtwo__intersections[i] = new_point """ Only intersection points contained in resp. other structure relevant """ INTone_intersections = [] INTtwo_intersections = [] if INTone__intersections != None: for i in range(0,len(INTone__intersections)): if self.INTtwo.contains(INTone__intersections[i]) == True: INTone_intersections.append(INTone__intersections[i]) if INTtwo__intersections != None: for j in range(0,len(INTtwo__intersections)): if self.INTone.contains(INTtwo__intersections[j]) == True: INTtwo_intersections.append(INTtwo__intersections[j]) """ => Convert to list """ INTone_set = set(INTone_intersections[:]) INTtwo_set = set(INTtwo_intersections[:]) combined_set = INTone_set | INTtwo_set combined_intersections = list(combined_set) """ Just in case... """ if len(combined_intersections) == 0: return None """ Sort by separation from ray origin """ intersection_separations = [] for point in combined_intersections: intersection_separations.append(separation(ray.position, point)) """ Convert into Numpy arrays in order to sort """ intersection_separations = np.array(intersection_separations) sorted_indices = intersection_separations.argsort() sorted_combined_intersections = [] for index in sorted_indices: sorted_combined_intersections.append(np.array(combined_intersections[index])) global_frame_intersections = [] for point in sorted_combined_intersections: global_frame_intersections.append(transform_point(point, self.transform)) return global_frame_intersections
def intersection(self, ray): """ Returns the intersection points of ray with CSGsub in global frame """ # We will need the invtransform later when we return the results..." invtransform = tf.inverse_matrix(self.transform) localray = Ray() localray.position = transform_point(ray.position, invtransform) localray.direction = transform_direction(ray.direction, invtransform) SUBplus__intersections = self.SUBplus.intersection(localray) SUBminus__intersections = self.SUBminus.intersection(localray) """ Cover the simpler cases """ if SUBplus__intersections == None and SUBminus__intersections == None: return None """ Change ..._intersections into tuples """ if SUBplus__intersections != None: for i in range(0,len(SUBplus__intersections)): point = SUBplus__intersections[i] new_point = (point[0], point[1], point[2]) SUBplus__intersections[i] = new_point if SUBminus__intersections != None: for i in range(0,len(SUBminus__intersections)): point = SUBminus__intersections[i] new_point = (point[0], point[1], point[2]) SUBminus__intersections[i] = new_point """ Valid intersection points: SUBplus intersections must lie outside SUBminus SUBminus intersections must lie inside SUBplus """ SUBplus_intersections = [] SUBminus_intersections = [] if SUBplus__intersections != None: for intersection in SUBplus__intersections: if not self.SUBminus.contains(intersection): SUBplus_intersections.append(intersection) if SUBminus__intersections != None: for intersection in SUBminus__intersections: if self.SUBplus.contains(intersection): SUBminus_intersections.append(intersection) # SUBplus_set = set(SUBplus_intersections[:]) # SUBminus_set = set(SUBminus_intersections[:]) # combined_set = SUBplus_set ^ SUBminus_set # combined_intersections = list(combined_set) combined_intersections = np.array(list(set(SUBplus_intersections+SUBminus_intersections))) # intersection_separations = combined_intersections[0]**2+combined_intersections[1]**2+combined_intersections[2]**2 """ Just in case... """ if len(combined_intersections) == 0: return None transposed_intersections = combined_intersections.transpose() intersection_vectors = transposed_intersections[0]-ray.position[0], transposed_intersections[1]-ray.position[1], transposed_intersections[2]-ray.position[2] # intersection_separations= [] # print combined_intersections, point, intersection_vectors intersection_separations = intersection_vectors[0]**2+intersection_vectors[1]**2+intersection_vectors[2]**2 # for point in combined_intersections: # intersection_separations.append(separation(ray.position, point)) # for i in range(len(intersection_separations)): # print intersection_separations[i], intersection_separations2[i] """ Sort by distance from ray origin => Use Numpy arrays """ # intersection_separations = np.array(intersection_separations) sorted_combined_intersections = combined_intersections[intersection_separations.argsort()] # sorted_combined_intersections = [] # for index in sorted_indices: # sorted_combined_intersections.append(np.array(combined_intersections[index])) # global_frame_intersections = [] # for point in sorted_combined_intersections: # global_frame_intersections.append(transform_point(point, self.transform)) global_frame_intersections = [transform_point(point, self.transform) for point in sorted_combined_intersections] return global_frame_intersections