예제 #1
0
void colorNorm (COLOR c)
/* Normalise colour channels to average of 1 */
{
   const float avg = colorAvg(c);
   
   if (!avg) 
      return;
      
   c [0] /= avg;
   c [1] /= avg;
   c [2] /= avg;
}
예제 #2
0
void distribPhotonContrib (PhotonMap* pm, unsigned numProc)
{
   EmissionMap       emap;
   char              errmsg2 [128], shmFname [PMAP_TMPFNLEN];
   unsigned          srcIdx, proc;
   int               shmFile, stat, pid;
   double            *srcFlux,         /* Emitted flux per light source */
                     srcDistribTarget; /* Target photon count per source */
   PhotonContribCnt  *photonCnt;       /* Photon emission counter array */
   unsigned          photonCntSize = sizeof(PhotonContribCnt) * 
                                     PHOTONCNT_NUMEMIT(nsources);
   FILE              **primaryHeap = NULL;
   char              **primaryHeapFname = NULL;
   PhotonPrimaryIdx  *primaryOfs = NULL;
                                    
   if (!pm)
      error(USER, "no photon map defined in distribPhotonContrib");
      
   if (!nsources)
      error(USER, "no light sources in distribPhotonContrib");

   if (nsources > MAXMODLIST)
      error(USER, "too many light sources in distribPhotonContrib");
      
   /* Allocate photon flux per light source; this differs for every 
    * source as all sources contribute the same number of distributed
    * photons (srcDistribTarget), hence the number of photons emitted per
    * source does not correlate with its emitted flux. The resulting flux
    * per photon is therefore adjusted individually for each source. */
   if (!(srcFlux = calloc(nsources, sizeof(double))))
      error(SYSTEM, "can't allocate source flux in distribPhotonContrib");

   /* ===================================================================
    * INITIALISATION - Set up emission and scattering funcs
    * =================================================================== */
   emap.samples = NULL;
   emap.src = NULL;
   emap.maxPartitions = MAXSPART;
   emap.partitions = (unsigned char*)malloc(emap.maxPartitions >> 1);
   if (!emap.partitions)
      error(USER, "can't allocate source partitions in distribPhotonContrib");

   /* Initialise contrib photon map */   
   initPhotonMap(pm, PMAP_TYPE_CONTRIB);
   initPhotonHeap(pm);
   initPhotonEmissionFuncs();
   initPhotonScatterFuncs();
   
   /* Per-subprocess / per-source target counts */
   pm -> distribTarget /= numProc;
   srcDistribTarget = nsources ? (double)pm -> distribTarget / nsources : 0;   
   
   if (!pm -> distribTarget)
      error(INTERNAL, "no photons to distribute in distribPhotonContrib");
   
   /* Get photon ports from modifier list */
   getPhotonPorts(photonPortList);
      
   /* Get photon sensor modifiers */
   getPhotonSensors(photonSensorList);      

#if NIX   
   /* Set up shared mem for photon counters (zeroed by ftruncate) */
   strcpy(shmFname, PMAP_TMPFNAME);
   shmFile = mkstemp(shmFname);
   
   if (shmFile < 0 || ftruncate(shmFile, photonCntSize) < 0)
      error(SYSTEM, "failed shared mem init in distribPhotonContrib");

   photonCnt = mmap(NULL, photonCntSize, PROT_READ | PROT_WRITE, 
                    MAP_SHARED, shmFile, 0);
                     
   if (photonCnt == MAP_FAILED)
      error(SYSTEM, "failed shared mem mapping in distribPhotonContrib");
#else
   /* Allocate photon counters statically on Windoze */
   if (!(photonCnt = malloc(photonCntSize)))
      error(SYSTEM, "failed trivial malloc in distribPhotonContrib");
   
   for (srcIdx = 0; srcIdx < PHOTONCNT_NUMEMIT(nsources); srcIdx++)
      photonCnt [srcIdx] = 0;
#endif /* NIX */

   if (verbose) {
      sprintf(errmsg, "\nIntegrating flux from %d sources", nsources);

      if (photonPorts) {
         sprintf(errmsg2, " via %d ports", numPhotonPorts);
         strcat(errmsg, errmsg2);
      }

      strcat(errmsg, "\n");
      eputs(errmsg);
   }

   /* =============================================================
    * FLUX INTEGRATION - Get total flux emitted from sources/ports
    * ============================================================= */   
   for (srcIdx = 0; srcIdx < nsources; srcIdx++) {
      unsigned portCnt = 0;      
      srcFlux [srcIdx] = 0;
      emap.src = source + srcIdx;
      
      do {  /* Need at least one iteration if no ports! */      
         emap.port = emap.src -> sflags & SDISTANT ? photonPorts + portCnt 
                                                   : NULL;
         photonPartition [emap.src -> so -> otype] (&emap);

         if (verbose) {
            sprintf(errmsg, "\tIntegrating flux from source %s ",
                    source [srcIdx].so -> oname);

            if (emap.port) {
               sprintf(errmsg2, "via port %s ", 
                       photonPorts [portCnt].so -> oname);
               strcat(errmsg, errmsg2);
            }

            sprintf(errmsg2, "(%lu partitions)\n", emap.numPartitions);
            strcat(errmsg, errmsg2);
            eputs(errmsg);
#if NIX            
            fflush(stderr);
#endif            
         }                    
         
         for (emap.partitionCnt = 0; emap.partitionCnt < emap.numPartitions;
              emap.partitionCnt++) {
            initPhotonEmission(&emap, pdfSamples);
            srcFlux [srcIdx] += colorAvg(emap.partFlux);
         }
         
         portCnt++;
      } while (portCnt < numPhotonPorts);         
      
      if (srcFlux [srcIdx] < FTINY) {
         sprintf(errmsg, "source %s has zero emission", 
                 source [srcIdx].so -> oname);
         error(WARNING, errmsg);
      }
   }   
   
   /* Allocate & init per-subprocess primary heap files */
   primaryHeap = calloc(numProc, sizeof(FILE*));
   primaryHeapFname = calloc(numProc, sizeof(char*));
   primaryOfs = calloc(numProc, sizeof(PhotonPrimaryIdx));
   if (!primaryHeap || !primaryHeapFname || !primaryOfs)
      error(SYSTEM, "failed primary heap allocation in "
            "distribPhotonContrib");
      
   for (proc = 0; proc < numProc; proc++) {
      primaryHeapFname [proc] = malloc(PMAP_TMPFNLEN);
      if (!primaryHeapFname [proc])
         error(SYSTEM, "failed primary heap file allocation in "
               "distribPhotonContrib");
               
      mktemp(strcpy(primaryHeapFname [proc], PMAP_TMPFNAME));
      if (!(primaryHeap [proc] = fopen(primaryHeapFname [proc], "w+b")))
         error(SYSTEM, "failed opening primary heap file in "
               "distribPhotonContrib");
   }               

   /* Record start time for progress reports */
   repStartTime = time(NULL);

   if (verbose) {
      sprintf(errmsg, "\nPhoton distribution @ %d procs\n", numProc);
      eputs(errmsg);
   }
               
   /* MAIN LOOP */
   for (proc = 0; proc < numProc; proc++) {
#if NIX          
      if (!(pid = fork())) {
         /* SUBPROCESS ENTERS HERE; opened and mmapped files inherited */
#else
      if (1) {
         /* No subprocess under Windoze */
#endif   
         /* Local photon counters for this subprocess */
         unsigned long  lastNumPhotons = 0, localNumEmitted = 0;
         double         photonFluxSum = 0;   /* Accum. photon flux */

         /* Seed RNGs from PID for decorellated photon distribution */
         pmapSeed(randSeed + proc, partState);
         pmapSeed(randSeed + (proc + 1) % numProc, emitState);
         pmapSeed(randSeed + (proc + 2) % numProc, cntState);
         pmapSeed(randSeed + (proc + 3) % numProc, mediumState);
         pmapSeed(randSeed + (proc + 4) % numProc, scatterState);
         pmapSeed(randSeed + (proc + 5) % numProc, rouletteState);

#ifdef PMAP_SIGUSR                       
   double partNumEmit;
   unsigned long partEmitCnt;
   double srcPhotonFlux, avgPhotonFlux;
   unsigned       portCnt, passCnt, prePassCnt;
   float          srcPreDistrib;
   double         srcNumEmit;     /* # to emit from source */
   unsigned long  srcNumDistrib;  /* # stored */

   void sigUsrDiags()
   /* Loop diags via SIGUSR1 */
   {
      sprintf(errmsg, 
              "********************* Proc %d Diags *********************\n"
              "srcIdx = %d (%s)\nportCnt = %d (%s)\npassCnt = %d\n"
              "srcFlux = %f\nsrcPhotonFlux = %f\navgPhotonFlux = %f\n"
              "partNumEmit = %f\npartEmitCnt = %lu\n\n",
              proc, srcIdx, findmaterial(source [srcIdx].so) -> oname, 
              portCnt, photonPorts [portCnt].so -> oname,
              passCnt, srcFlux [srcIdx], srcPhotonFlux, avgPhotonFlux,
              partNumEmit, partEmitCnt);
      eputs(errmsg);
      fflush(stderr);
   }
#endif
         
#ifdef PMAP_SIGUSR
         signal(SIGUSR1, sigUsrDiags);
#endif         

#ifdef DEBUG_PMAP          
         /* Output child process PID after random delay to prevent corrupted
          * console output due to race condition */
         usleep(1e6 * pmapRandom(rouletteState));
         fprintf(stderr, "Proc %d: PID = %d "
                 "(waiting 10 sec to attach debugger...)\n", 
                 proc, getpid());
         /* Allow time for debugger to attach to child process */
         sleep(10);
#endif

         /* =============================================================
          * 2-PASS PHOTON DISTRIBUTION
          * Pass 1 (pre):  emit fraction of target photon count
          * Pass 2 (main): based on outcome of pass 1, estimate remaining 
          *                number of photons to emit to approximate target 
          *                count
          * ============================================================= */
         for (srcIdx = 0; srcIdx < nsources; srcIdx++) {
#ifndef PMAP_SIGUSR         
            unsigned       portCnt, passCnt = 0, prePassCnt = 0;
            float          srcPreDistrib = preDistrib;
            double         srcNumEmit = 0;       /* # to emit from source */
            unsigned long  srcNumDistrib = pm -> numPhotons;  /* # stored */
#else
            passCnt = prePassCnt = 0;
            srcPreDistrib = preDistrib;
            srcNumEmit = 0;       /* # to emit from source */
            srcNumDistrib = pm -> numPhotons;  /* # stored */
#endif            

            if (srcFlux [srcIdx] < FTINY)
               continue;
                        
            while (passCnt < 2) {
               if (!passCnt) {   
                  /* INIT PASS 1 */
                  if (++prePassCnt > maxPreDistrib) {
                     /* Warn if no photons contributed after sufficient
                      * iterations; only output from subprocess 0 to reduce
                      * console clutter */
                     if (!proc) {
                        sprintf(errmsg, 
                                "source %s: too many prepasses, skipped",
                                source [srcIdx].so -> oname);
                        error(WARNING, errmsg);
                     }

                     break;
                  }
                  
                  /* Num to emit is fraction of target count */
                  srcNumEmit = srcPreDistrib * srcDistribTarget;
               }
               else {
                  /* INIT PASS 2 */
#ifndef PMAP_SIGUSR
                  double srcPhotonFlux, avgPhotonFlux;
#endif
                  
                  /* Based on the outcome of the predistribution we can now
                   * figure out how many more photons we have to emit from
                   * the current source to meet the target count,
                   * srcDistribTarget. This value is clamped to 0 in case
                   * the target has already been exceeded in pass 1.
                   * srcNumEmit and srcNumDistrib is the number of photons
                   * emitted and distributed (stored) from the current
                   * source in pass 1, respectively. */
                  srcNumDistrib = pm -> numPhotons - srcNumDistrib;
                  srcNumEmit *= srcNumDistrib 
                                ? max(srcDistribTarget/srcNumDistrib, 1) - 1
                                : 0;

                  if (!srcNumEmit)
                     /* No photons left to distribute in main pass */
                     break;
                     
                  srcPhotonFlux = srcFlux [srcIdx] / srcNumEmit;
                  avgPhotonFlux = photonFluxSum / (srcIdx + 1);
                  
                  if (avgPhotonFlux > FTINY && 
                      srcPhotonFlux / avgPhotonFlux < FTINY) {
                     /* Skip source if its photon flux is grossly below the
                      * running average, indicating negligible contributions
                      * at the expense of excessive distribution time; only
                      * output from subproc 0 to reduce console clutter */
                     if (!proc) {
                        sprintf(errmsg, 
                                "source %s: itsy bitsy photon flux, skipped",
                                source [srcIdx].so -> oname);                     
                        error(WARNING, errmsg);
                     }

                     srcNumEmit = 0;   /* Or just break??? */
                  }
                        
                  /* Update sum of photon flux per light source */
                  photonFluxSum += srcPhotonFlux;
               }
                              
               portCnt = 0;
               do {    /* Need at least one iteration if no ports! */
                  emap.src = source + srcIdx;
                  emap.port = emap.src -> sflags & SDISTANT 
                              ? photonPorts + portCnt : NULL;
                  photonPartition [emap.src -> so -> otype] (&emap);

                  if (verbose && !proc) {
                     /* Output from subproc 0 only to avoid race condition
                      * on console I/O */
                     if (!passCnt)
                        sprintf(errmsg, "\tPREPASS %d on source %s ",
                                prePassCnt, source [srcIdx].so -> oname);
                     else 
                        sprintf(errmsg, "\tMAIN PASS on source %s ",
                                source [srcIdx].so -> oname);

                     if (emap.port) {
                        sprintf(errmsg2, "via port %s ", 
                                photonPorts [portCnt].so -> oname);
                        strcat(errmsg, errmsg2);
                     }

                     sprintf(errmsg2, "(%lu partitions)\n",
                             emap.numPartitions);
                     strcat(errmsg, errmsg2);                     
                     eputs(errmsg);
#if NIX                     
                     fflush(stderr);
#endif                     
                  }                
                  
                  for (emap.partitionCnt = 0; emap.partitionCnt < emap.numPartitions; 
                       emap.partitionCnt++) {
#ifndef PMAP_SIGUSR                       
                     double partNumEmit;
                     unsigned long partEmitCnt;
#endif
                     
                     /* Get photon origin within current source partishunn
                      * and build emission map */
                     photonOrigin [emap.src -> so -> otype] (&emap);
                     initPhotonEmission(&emap, pdfSamples);
                     
                     /* Number of photons to emit from ziss partishunn;
                      * scale according to its normalised contribushunn to
                      * the emitted source flux */                     
                     partNumEmit = srcNumEmit * colorAvg(emap.partFlux) /
                                   srcFlux [srcIdx];                    
                     partEmitCnt = (unsigned long)partNumEmit;
                                                               
                     /* Probabilistically account for fractional photons */
                     if (pmapRandom(cntState) < partNumEmit - partEmitCnt)
                        partEmitCnt++;
                        
                     /* Update local and shared global emission counter */
                     photonCnt [PHOTONCNT_NUMEMIT(srcIdx)] += partEmitCnt;
                     localNumEmitted += partEmitCnt;                                    
                     
                     /* Integer counter avoids FP rounding errors during
                      * iteration */
                     while (partEmitCnt--) {
                        RAY photonRay;
                     
                        /* Emit photon according to PDF (if any), allocate
                         * associated primary ray, and trace through scene
                         * until absorbed/leaked; emitPhoton() sets the
                         * emitting light source index in photonRay */
                        emitPhoton(&emap, &photonRay);
#if 1
                        if (emap.port)
                           /* !!!  PHOTON PORT REJECTION SAMPLING HACK: set
                            * !!!  photon port as fake hit object for
                            * !!!  primary ray to check for intersection in
                            * !!!  tracePhoton() */                        
                           photonRay.ro = emap.port -> so;
#endif
                        newPhotonPrimary(pm, &photonRay, primaryHeap[proc]);
                        /* Set subprocess index in photonRay for post-
                         * distrib primary index linearisation; this is
                         * propagated with the primary index in photonRay
                         * and set for photon hits by newPhoton() */
                        PMAP_SETRAYPROC(&photonRay, proc);
                        tracePhoton(&photonRay);
                     }
                     
                     /* Update shared global photon count */                     
                     photonCnt [PHOTONCNT_NUMPHOT] += pm -> numPhotons - 
                                                      lastNumPhotons;
                     lastNumPhotons = pm -> numPhotons;
#if !NIX
                     /* Synchronous progress report on Windoze */
                     if (!proc && photonRepTime > 0 && 
                           time(NULL) >= repLastTime + photonRepTime) {
                        unsigned s;                        
                        repComplete = pm -> distribTarget * numProc;
                        repProgress = photonCnt [PHOTONCNT_NUMPHOT];
                        
                        for (repEmitted = 0, s = 0; s < nsources; s++)
                           repEmitted += photonCnt [PHOTONCNT_NUMEMIT(s)];

                        pmapDistribReport();
                     }
#endif
                  }

                  portCnt++;
               } while (portCnt < numPhotonPorts);                  

               if (pm -> numPhotons == srcNumDistrib) {
                  /* Double predistrib factor in case no photons were stored
                   * for this source and redo pass 1 */
                  srcPreDistrib *= 2;
               }
               else {
                  /* Now do pass 2 */
                  passCnt++;
               }
            }
         }
                        
         /* Flush heap buffa one final time to prevent data corruption */
         flushPhotonHeap(pm);         
         /* Flush final photon primary to primary heap file */
         newPhotonPrimary(pm, NULL, primaryHeap [proc]);
         /* Heap files closed automatically on exit
            fclose(pm -> heap);
            fclose(primaryHeap [proc]); */
                  
#ifdef DEBUG_PMAP
         sprintf(errmsg, "Proc %d total %ld photons\n", proc, 
                 pm -> numPhotons);
         eputs(errmsg);
         fflush(stderr);
#endif

#ifdef PMAP_SIGUSR
         signal(SIGUSR1, SIG_DFL);
#endif

#if NIX
         /* Terminate subprocess */
         exit(0);
#endif
      }
      else if (pid < 0)
// ######################################################################
Image<PixRGB<byte> > SuperPixelRoadSegmenter::getSuperPixel(Image<PixRGB<byte> > img)
{
    if(!img.initialized()) return Image<PixRGB<byte> >(320,240,ZEROS);

    // default parameters for the Superpixel segmentation
    float sigma = .5;
    uint k = 400;
    uint minSize = 100;
    int num_ccs;
    std::vector<std::vector<Point2D<int> > > groups;
    Image<int> groupImage =
        SuperPixelSegment(img,sigma, k, minSize, num_ccs, &groups);
    Image<PixRGB<byte> > sp_img = SuperPixelDebugImage(groups,img);
    Image<int> sp_size_img = SuperPixelRegionSizeImage(groups,groupImage);
    itsRawSuperPixelImg = sp_img;
    //debugWin(itsRawSuperPixelImg,"itsRawSuperPixelImg");
    int w = sp_img.getWidth();
    int h = sp_img.getHeight();

    // Look for road color,
    // let's assume it always show up in the middle bottom (h-5,w/2 +- 10)

    std::vector<PixRGB<byte> >	color_map;
    std::vector<int>	color_size_map;
    std::vector<int> 	color_map_count;

    // Pick all road pixel candidates
    int windowL = -SEARCH_WINDOW_W/2; //-10
    int windowR =  SEARCH_WINDOW_W/2; // 10
    int windowB =  SEARCH_WINDOW_BOTTOM;
    int windowT =  SEARCH_WINDOW_H;
    for(int i = windowL; i<= windowR; i++)
    {
        //We are search bottom area as most likely road pixel candidates
        for(int k = windowB; k <=windowT; k++) {

            //set our grow window float to the middle of road
            int middlePoint;
            if(itsMiddlePoint[k-1]!=0 && itsUseFloatWindow) {
                middlePoint = itsMiddlePoint[k-1]/4;//1/4 size image
                //LINFO("Float Window %d midpoint %d",middlePoint,k-1);
            } else {

                middlePoint = w/2;
                //LINFO("Fixed Window %d midpoint",middlePoint);
            }
            if(sp_img.coordsOk(middlePoint+i,h-k)) {
                PixRGB<byte> tmp_color = sp_img.getVal(middlePoint + i,h-k);
                int regionSize = sp_size_img.getVal(middlePoint+i,h-k);

                bool notfound = true;

                // Search color
                for(int j = 0; j < (int)color_map.size() && notfound ; j++)
                {
                    if(color_map[j] == tmp_color)
                    {
                        notfound = false;
                        color_map_count[j]++;
                    }
                }
                if(notfound)
                {
                    color_map.push_back(tmp_color);
                    color_map_count.push_back(0);
                    color_size_map.push_back(regionSize);
                }
            }
        }
    }

    if(color_map.size() > 1)
    {   //if we found more than one color
        //Some Option Here:
        //1.Choose max count color
        //2.Pick min color difference from previous avg road color pixel

        //if road color is not available, we pick max pixel color
        if(itsRoadColor == PixRGB<byte>(0,0,0)) {
            int max = color_map_count[0];
            int max_index = 0;
            for(int i = 1; i < (int)color_map_count.size() ; i++)
            {
                if(max < color_map_count[i])
                {
                    max = color_map_count[i];
                    max_index = i;
                }
            }
            itsRoadColor = color_map[max_index];
            //LINFO("Max count color have count %d",max);
        } else {
            //Pick min color difference color
            int min_index = 0;
            float min = colorDiff(itsRoadColor,color_map[0]);//
            for(int i = 1; i < (int)color_map_count.size() ; i++)
            {
                float cd = colorDiff(itsRoadColor,color_map[i]);
                int rs = color_size_map[i];//region size
                //LINFO("Road Region Size %d",rs);
                if(cd < min && rs > 100)
                {
                    min = cd;
                    min_index = i;
                }
            }
            itsRoadColorDiff = colorDiff(itsRoadColor,color_map[min_index]);

            //to prevent jump too much
            if(itsRoadColorDiff < 50.0) {
                itsRoadColor = color_map[min_index];
            } else {
                //keep avg color so it will help to solve kid-napping problem
                PixRGB<byte> avgColor = colorAvg(itsRoadColor,color_map[0],0.8);//first color will have 80% weight
                itsRoadColor = avgColor;
                //LINFO("COLOR DIFF1 %f",itsRoadColorDiff);
            }
        }
    }
    else
    {
        //if only one region
        itsRoadColorDiff = colorDiff(itsRoadColor,color_map[0]);
        itsRoadColorDiffSub = colorDiffSub(itsRoadColor,color_map[0]);


        if((itsRoadColorDiff < 50.0 && color_map[0].green() > 150)||itsRoadColor == PixRGB<byte>(0,0,0)) { //for outdoor concrete road
            //if((itsRoadColorDiff < 90.0 && color_map[0].green()<150)||itsRoadColor == PixRGB<byte>(0,0,0)){//indoor
            //if((itsRoadColorDiff < 90.0)||itsRoadColor == PixRGB<byte>(0,0,0)){//general, high fail rate
            itsRoadColor = color_map[0];
            //itsUseFloatWindow = false;//FIXXXXXX
        } else {
            PixRGB<byte> avgColor = colorAvg(itsRoadColor,color_map[0],0.8);//80% on first one
            itsRoadColor = avgColor;
            itsUseFloatWindow = true;
            //LINFO("COLOR DIFF2 %f,USE float window",itsRoadColorDiff);
        }
        //LINFO("Only one color (%d,%d,%d)",itsRoadColor.red(),itsRoadColor.green(),itsRoadColor.blue());
    }

    // use iterator!!!!!!
    Image<PixRGB<byte> > output(w,h,ZEROS); //image with full red road region
    Image<PixRGB<byte> > hybrid(w,h,ZEROS); //image with red grid dot road region
    itsRoadIndexMap = Image<int>(w, h, ZEROS);
    //	inplacePaste(output, sp_img, Point2D<int>(w, 0));
    for(int y = 0 ; y < h ; y ++)
    {
        int dot = 0;
        for(int x = 0 ; x < w ; x ++)
        {
            PixRGB<byte> c = sp_img.getVal(x,y);
            //LINFO("Pixel color(%d,%d,%d)road color(%d,%d,%d)",c.red(),c.green(),c.blue(),
            //		itsRoadColor.red(),itsRoadColor.green(),itsRoadColor.blue());
            if(c == itsRoadColor)	{
                //Set road color to red
                byte red = 250+c.red();
                if(red > 255) red = 255;
                //output.setVal(x,y,PixRGB<byte>(red,c.green()/32,c.blue()/32));//this will mess up find red region
                output.setVal(x,y,PixRGB<byte>(255,0,0));
                itsRoadIndexMap.setVal(x,y,255);
                if(dot % 3 == 0) {
                    hybrid.setVal(x,y,PixRGB<byte>(255,0,0));
                } else {
                    hybrid.setVal(x,y,c);
                }
                dot ++;
            }
            else {
                //set to it's color
                output.setVal(x,y,c);
                hybrid.setVal(x,y,c);
                itsRoadIndexMap.setVal(x,y,0);
                //					output.setVal(x,y,c);
            }
        }
    }
    LINFO("hi11");
    if(!output.initialized())
        return img;

    LINFO("hi12");
    //LINFO("Finish Road Finding");
    itsRawRoadSuperPixelImg = hybrid;
    return output;
}