Yalantis/uCrop · error · CImgInstanceException

CImgList<%s>::FFT(): Empty specified real part.

Error message

CImgList<%s>::FFT(): Empty specified real part.

What it means

The static CImg<T>::FFT(real, imag, ...) entry point first checks that the real-part image is non-empty (operator! fails on empty instances, i.e. any zero dimension or null data). An empty real part has nothing to transform, so CImg throws this CImgInstanceException before doing any work. The imaginary part may be empty (it is then zero-filled), but the real part may not.

Source

Thrown at ucrop/src/main/jni/CImg.h:47930

        }
        if (is_inverse) { real/=N; imag/=N; }
      } break;
      }
#endif
    }

    //! Compute n-D Fast Fourier Transform.
    /**
       \param[in,out] real Real part of the pixel values.
       \param[in,out] imag Imaginary part of the pixel values.
       \param is_inverse Tells if the forward (\c false) or inverse (\c true) FFT is computed.
       \param nb_threads Number of parallel threads used for the computation.
         Use \c 0 to set this to the number of available cpus.
    **/
    static void FFT(CImg<T>& real, CImg<T>& imag, const bool is_inverse=false,
                    const unsigned int nb_threads=0) {
      if (!real)
        throw CImgInstanceException("CImgList<%s>::FFT(): Empty specified real part.",
                                    pixel_type());
      if (!imag) imag.assign(real._width,real._height,real._depth,real._spectrum,(T)0);
      if (!real.is_sameXYZC(imag))
        throw CImgInstanceException("CImgList<%s>::FFT(): Specified real part (%u,%u,%u,%u,%p) and "
                                    "imaginary part (%u,%u,%u,%u,%p) have different dimensions.",
                                    pixel_type(),
                                    real._width,real._height,real._depth,real._spectrum,real._data,
                                    imag._width,imag._height,imag._depth,imag._spectrum,imag._data);
      cimg::unused(nb_threads);
#ifdef cimg_use_fftw3
      cimg::mutex(12);
#ifndef cimg_use_fftw3_singlethread
      fftw_plan_with_nthreads(nb_threads?nb_threads:cimg::nb_cpus());
#endif
      fftw_complex *data_in = (fftw_complex*)fftw_malloc(sizeof(fftw_complex)*real._width*real._height*real._depth);
      if (!data_in)
        throw CImgInstanceException("CImgList<%s>::FFT(): Failed to allocate memory (%s) "
                                    "for computing FFT of image (%u,%u,%u,%u).",

View on GitHub (pinned to f788b534b4)

Solutions

  1. Ensure the real image is properly constructed/loaded before calling FFT (check real.data() or if (real)).
  2. Check the return of load()/IO calls: an empty image usually means the load failed; fix the file path or format first.
  3. If the imaginary part is what you have, swap the arguments: FFT(imag, real) is not valid, but you can FFT a real image with an empty imag and it will be zero-filled.
  4. Guard with if (!real) throw/log before calling FFT.

Example fix

// before
CImg<float> real; // default-constructed, empty
CImg<float>::FFT(real, imag);
// after
CImg<float> real("input.png");
if (real) CImg<float>::FFT(real, imag);
Defensive patterns

Strategy: validation

Validate before calling

if (!real || !real.data()) throw std::invalid_argument("FFT real part must be non-empty");

Type guard

bool isNonEmpty(const CImg<T>& img) { return (bool)img && img.data() != nullptr; }

Try / catch

try { CImg<float>::FFT(real, imag); }
catch (CImgInstanceException& e) { std::cerr << "Empty real part: check that the image loaded correctly"; }

Prevention

When it happens

Trigger: Passing a default-constructed CImg<T>() or an assign()-cleared image as the real argument to the static FFT(real, imag, is_inverse, nb_threads); also passing an image whose data failed to load (e.g. load() on a missing file returned an empty image).

Common situations: Image loading failed silently earlier in the pipeline (empty result of CImg::load), wrong variable passed, or reusing an image after assign() without re-allocating it.

Understand the failure class

Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.

Related errors


AI-assisted analysis of Yalantis/uCrop@f788b534b4 (2026-09-08). Data as JSON: /api/errors/4049caf62f77180f. Report an issue: GitHub.