Example #1
0
def Demarrer():
    """ Démarre l'animation """
    global Arret

    # 
    # Preparation de la scene à rendre
    #
    # theScene.load("xmlfile")
    # pos = vec3(0,0,10)
    # theScene.insert( Sphere( pos, 1, "bouboule", Material( color(1,0,0) ) ) )

    # pos = vec3(-1,0,8)
    # theScene.insert( Sphere( pos, 1, "bouboule2", Material( color(0,1,0) ) ) )

    # pos = vec3(1,0,12)
    # theScene.insert( Sphere( pos, 1, "bouboule3", Material( color(0,0,1) ) ) )
    
    # for p in range(0,10):
    #     x = int(random.triangular()*RenderParam.width)
    #     y = int(random.triangular()*RenderParam.height)
    #     Img.put( "#FFF", (x, y) )


    ###############
    pos = vec3(2,4,8)
    theScene.insert( Sphere( pos, 2, "light", Material( color(1,1,1), pEmissivity=8.0 ) ) )
    pos = vec3(0,0.5,8)
    theScene.insert( Sphere( pos, 0.8, "bouboule2", Material( color(0,1,0) ) ) )
    pos = vec3(0,-1.2,8)
    theScene.insert( Sphere( pos, 0.8, "bouboule3", Material( color(0,0,1) ) ) )


    pos = vec3(0,0,0)
    up = vec3(0,1,0)
    direction = vec3(0,0,1)

    cam = Camera( pos, up, direction, "macam" )
    theScene.insert( cam )
    theScene.setActiveCamera( cam )

    theRenderer.setScene( theScene )
    theRenderer.reset()

    # print theScene.getObject("bouboule")
    # print theScene.getObject("macam")
    # print "activeCam: %r" % theScene.getObject("macam")

    if Arret == True:
        Arret = False
        RenderPixel()
    def renderPixel(self, pX, pY):
        """ """
        currColor = color(0,0,0)

        for dX in RenderParam.sampling:
            for dY in RenderParam.sampling:
                for samples in range(0, RenderParam.renderSampling):
                    sx = random.triangular()
                    sy = random.triangular()

                    currColor += self.radiance( self.getCurrentRay( pX+dX+sx, pY+dY+sy), 0 )

                # currColor += self.radiance( self.getCurrentRay( pX+dX, pY+dY), 0 )

        res = currColor / (RenderParam.subSampling*RenderParam.subSampling*RenderParam.renderSampling) 
        
        # Normalize color exposure
        res._r = 1.0 - math.exp(res._r * RenderParam.exposure); 
        res._g = 1.0 - math.exp(res._g * RenderParam.exposure); 
        res._b = 1.0 - math.exp(res._b * RenderParam.exposure); 

        return (res*255).hexa()
    def radiance(self, pRay, pDepth):
        """ """
        pDepth += 1
        self._stats['numCallRadiance'] += 1

        if RenderParam.maxDepth < pDepth:
            return RenderParam.backgroundColor
        
        # if pDepth > 2:
        #     print "pDepth:%d - ray: %s" % (pDepth, pRay)

        #
        # Find intersection
        #
        intersectionDict = {}
        for item in self._scene:
            # print "checking object %s with ray %r" % (item._name, pRay)
            intersectInfo = item.intersect(pRay)
            if intersectInfo is not None:
                intersectionDict[ intersectInfo['distance'] ] = intersectInfo

        if len(intersectionDict) is not 0:
            closest = intersectionDict[sorted(intersectionDict.keys())[0]]
        else:
            return RenderParam.backgroundColor
        
        currObj = closest['object']
        intersectColor = copy(currObj._mat._color)

        #
        # Stop recursion
        #
        # maxTerm = currObj._mat._color.maxTerm()
        # if 5 < pDepth or maxTerm is not 0:
        
        # if RenderParam.maxDepth < pDepth:
        #     # if russian roulette result < maxTerm:
        #     #     intersectColor /= maxTerm
        #     # else:
        #     resColor = currObj._mat._color * currObj._mat._emissivity
        #     return resColor


        #
        # refract term
        #

        #
        # reflect term
        #

        #
        # diffuse term
        #
        r1 = 2*pi*random.uniform(0.0,1.0)
        r2 = random.uniform(0.0,1.0)
        r2s = math.sqrt(r2)
        w = closest['orientedNormal']
        tmp = vec3(0,1,0) if (math.fabs(w.x)>0.1) else vec3(1,0,0)
        u = vec3.crossProduct(tmp,w).normalize()
        v = vec3.crossProduct(w,u)

        newDir = ( u*cos(r1)*r2s + v*sin(r1)*r2s + w*math.sqrt(1-r2)).normalize()
        newRay = Ray( closest['pos'], newDir )

        # # print "sampleColor for %s at depth %d" % (newRay, pDepth) 

        sampledColor = self.radiance( newRay, pDepth )
        # sampledColor = color(0)

        # IS term: iterate over all lights
        importanceSamplingTerm = color(0.0,0.0,0.0)
        for light in self._scene:
            if  (light._visible==True and hasattr(light,'_mat') \
                and light._mat._emissivity > 0) \
                and light is not currObj:

                # sw = light._pos - closest['pos']
                # if 0.1 < math.fabs(sw.x):
                #     su = vec3(0,1,0)
                # else:
                #     su = vec3(1,0,0)
                # sv = vec3.crossProduct(sw, su)

                # tmp = (closest['pos']-light._pos) * (closest['pos']-light._pos)
                # cos_a_max = math.sqrt( 1 - (light._radius*light._radius) / tmp )

                # eps1 = random.uniform(0,1)
                # eps2 = random.uniform(0,1)
                # cos_a = 1 - eps1 + eps1*cos_a_max
                # sin_a = math.sqrt( 1 - cos_a*cos_a )
                # phi = 2*pi*eps2

                # # # Create random direction
                # lightVec = su*math.cos(phi)*sin_a + \
                #             sv*math.sin(phi)*sin_a + \
                #             sw*cos_a
                # lightVec.normalize()

                # ou alors avec un vecteur direct intersection -> lum
                lightVec = light._pos - closest['pos']
                lightVec.normalize()
                
                tmp = lightVec * closest['normal']
                if 0<tmp:
                    # importanceSamplingTerm = tmp*0.1 * currObj._mat._color * light._mat._emissivity
                    # Shoot shadow ray
                    shadowIntersectionDict = {}
                    for item in self._scene:
                        shadowIntersectInfo = item.intersect( Ray(closest['pos'], lightVec) )
                        if shadowIntersectInfo is not None:
                            shadowIntersectionDict[ shadowIntersectInfo['distance'] ] = shadowIntersectInfo

                    # print len(shadowIntersectionDict)
                    if len(shadowIntersectionDict) != 0:
                        closestLight = shadowIntersectionDict[sorted(shadowIntersectionDict.keys())[0]]
                        print "closest %r, emit:%f" % (closestLight['object'], closestLight['object']._mat._emissivity)
                        if closestLight['object']._mat._emissivity > 0:
                            importanceSamplingTerm = tmp*0.1 * currObj._mat._color * light._mat._emissivity


                # else:
                #     importanceSamplingTerm = color(0,1,0)

                # Shoot shadow ray
                # shadowIntersectionDict = {}
                # for item in self._scene:
                #     shadowIntersectInfo = item.intersect(Ray(closest['pos'], lightVec))
                #     if shadowIntersectInfo is not None:
                #         shadowIntersectionDict[ shadowIntersectInfo['distance'] ] = shadowIntersectInfo

                # if len(shadowIntersectionDict) is not 0:
                #     closest = intersectionDict[sorted(intersectionDict.keys())[0]]
                #     if closest['object'] is light:
                #         omega = 2 * pi * (1 - cos_a_max)
                #         importanceSamplingTerm = currObj._mat._color * light._mat._emissivity * (lightVec * closest['orientedNormal']) * (omega /pi)
                    # else:
                    #     #pb ici!...
                    #     importanceSamplingTerm = color(1,0,0)

        # return EMISSIVE TERM + IS TERM + MIX INTERSECTION AND SAMPLES
        # return (currObj._mat._color*currObj._mat._emissivity + importanceSamplingTerm + intersectColor*sampledColor)
        # return (sampledColor)
        return ( importanceSamplingTerm )