Exemple #1
0
void Integral::IntegralScan(IImage& Source, IImage& Dest)
{
   PrepareFor(Source);

   CheckSameSize(Source, Dest);
   CheckFloat(Dest);

   uint Width = Source.Width();
   uint Height = Source.Height();

   Kernel(scan1, Source, Dest, Width, Height);

   if (GetNbGroupsW(Source) > 1)
   {
      make_kernel<Image2D, Image2D>(SelectProgram(Dest), "scan2")
         (EnqueueArgs(*m_CL, NDRange(GetNbGroupsW(Source) - 1, Source.Height())), Dest, *m_VerticalJunctions);
   }

#undef KERNEL_RANGE
#define KERNEL_RANGE(src_img) src_img.FullRange()

   Kernel(scan3, In(Dest, *m_VerticalJunctions), Dest);

   if (GetNbGroupsH(Source) > 1)
   {
      make_kernel<Image2D, Image2D>(SelectProgram(Dest), "scan4")
         (EnqueueArgs(*m_CL, NDRange(Source.Width(), GetNbGroupsH(Source) - 1)), Dest, *m_HorizontalJunctions);
   }

   Kernel(scan5, In(Dest, *m_HorizontalJunctions), Dest);
}
void ImageProximityFFT::PrepareFor(ImageBase& Source, Image& Template)
{
   SSize size;

   size.Width = Source.Width();
   size.Height = Source.Height();

   if (m_image_sqsums == nullptr || m_image_sqsums->Width() < size.Width || m_image_sqsums->Height() < size.Height)
      m_image_sqsums = std::make_shared<TempImage>(*m_CL, size, SImage::F32, Source.NbChannels());


   // Size of the FFT input and output
   size.Width = Source.Width() + Template.Width() / 2;
   size.Height = Source.Height() + Template.Height() / 2;

   // Search for a size supported by clFFT
   while (!m_fft.IsSupportedLength(size.Width))
      size.Width++;

   while (!m_fft.IsSupportedLength(size.Height))
      size.Height++;

   if (m_bigger_source == nullptr || m_bigger_source->Width() != size.Width || m_bigger_source->Height() != size.Height)
      m_bigger_source = std::make_shared<TempImage>(*m_CL, size, SImage::F32, 1);

   if (m_bigger_template == nullptr || m_bigger_template->Width() < size.Width || m_bigger_template->Height() < size.Height)
      m_bigger_template = std::make_shared<TempImage>(*m_CL, size, SImage::F32, 1);



   // Size of the spectral images
   size.Width = size.Width / 2 + 1;

   if (m_templ_spect == nullptr || m_templ_spect->Width() < size.Width || m_templ_spect->Height() < size.Height)
      m_templ_spect = std::make_shared<TempImage>(*m_CL, size, SImage::F32, 2);

   if (m_source_spect == nullptr || m_source_spect->Width() != size.Width || m_source_spect->Height() != size.Height)
      m_source_spect = std::make_shared<TempImage>(*m_CL, size, SImage::F32, 2);

   if (m_result_spect == nullptr || m_result_spect->Width() < size.Width || m_result_spect->Height() < size.Height)
      m_result_spect = std::make_shared<TempImage>(*m_CL, size, SImage::F32, 2);

   m_integral.PrepareFor(Source);
   m_statistics.PrepareFor(Template);
   m_transform.PrepareFor(Source);
   m_fft.PrepareFor(*m_bigger_source, *m_source_spect);
   SelectProgram(Source).Build();
   SelectProgram(*m_source_spect).Build();
}
void Statistics::InitAbs(Image& Source)
{
    Source.SendIfNeeded();

    cl::make_kernel<cl::Buffer, cl::Buffer>(SelectProgram(Source), "init_abs")
    (cl::EnqueueArgs(*m_CL, cl::NDRange(1, 1, 1)), Source, m_ResultBuffer);
}
void ImageProximityFFT::Convolve(Image& Source, Image& Template, Image& Dest)
{
   CheckSameSize(Source, Dest);

   PrepareFor(Source, Template);

   // Fill these images with black
   m_transform.SetAll(*m_bigger_template, 0);
   m_transform.SetAll(*m_bigger_source, 0);

   for (uint i = 1; i <= Source.NbChannels(); i++)
   {
      // Copy the data from Source and Template in images that are F32 and are big enough
      Kernel(copy_offset, In(Source), Out(*m_bigger_source), Source.Step(), m_bigger_source->Step(),
         int(Template.Width()) / 2, int(Template.Height()) / 2, m_bigger_source->Width(), m_bigger_source->Height(), i);

      Kernel(copy_offset, In(Template), Out(*m_bigger_template), Template.Step(), m_bigger_template->Step(),
         0, 0, m_bigger_template->Width(), m_bigger_template->Height(), i);


      // Forward FFT of Source and Template
      m_fft.Forward(*m_bigger_source, *m_source_spect);
      m_fft.Forward(*m_bigger_template, *m_templ_spect);


      // We need to divide the values by the FFT area to get the proper 
      float Area = float(m_bigger_source->Width() * m_bigger_source->Height());

      // Do the convolution using pointwise product of the spectrums
      // See information here : http://en.wikipedia.org/wiki/Convolution_theorem
      MulAndScaleSpectrums(*m_source_spect, *m_templ_spect, *m_result_spect, 1 / Area);


      // Inverse FFT to get the result of the convolution
      m_fft.Inverse(*m_result_spect, *m_bigger_source);  // Reuse m_bigger_source image for the convolution result


      // Copy the result to Dest
      Kernel_(*m_CL, SelectProgram(Dest), copy_result, m_bigger_source->FullRange(), LOCAL_RANGE,
         In(*m_bigger_source), Out(Dest), m_bigger_source->Step(), Dest.Step(), Dest.Width(), Dest.Height(), i);
   }

}
Exemple #5
0
void VectorProgram::PrepareFor(const ImageBase& Source)
{
   SelectProgram(Source).Build();
}
Exemple #6
0
Program& ImageProgram::SelectProgram(const ImageBase& Img1, const ImageBase&, const ImageBase&, const ImageBase&)
{
   // Only Img1 is used to select the program
   return SelectProgram(Img1);
}