#include "Resample/Sample/ReSample.h"

#include "Sample/Aggregate/Crystal2D.h"
#include "Sample/HardParticle/Cylinder.h"
#include "Sample/Material/RefractiveMaterial.h"
#include "Sample/Multilayer/Layer.h"
#include "Sample/Option/SimulationOptions.h"
#include "Sample/Particle/Particle.h"
#include "Sample/Sample/Sample.h"
#include "Tests/GTestWrapper/google_test.h"

TEST(MultilayerAveraging, AverageMultilayer)
{
    const auto mat0 = RefractiveMaterial("vac", MaterialColor(0.9, 0.93, 0.97), 0.0, 0.0);
    const auto mat1 = RefractiveMaterial("stone", MaterialColor(0.4, 0.4, 0.4), 4e-4, 8e-7);

    // particles
    Cylinder cylinder_ff(1.0, 3.0);
    Particle particle(mat1, cylinder_ff);

    // interferences
    Crystal2D interf_1(particle, BasicLattice2D(10.0, 10.0, 120.0, 0.0));
    Crystal2D interf_2(particle, BasicLattice2D(10.0, 10.0, 120.0, 0.0));

    Layer layer1(mat0);
    Layer layer2(mat1);

    layer1.deposit2D(interf_1);

    Sample sample;
    sample.addLayer(layer1);
    sample.addLayer(layer2);

    SimulationOptions options;
    options.setUseAvgMaterials(false);

    const auto re_sample1 = ReSample::processedSample(sample, options);

    Layer layer21(mat0);
    Layer layer22(mat1);

    layer21.deposit2D(interf_1);
    layer21.deposit2D(interf_2);

    Sample sample2;
    sample2.addLayer(layer21);
    sample2.addLayer(layer22);

    const auto re_sample2 = ReSample::processedSample(sample2, options);

    EXPECT_EQ(re_sample1.numberOfSlices(), re_sample2.numberOfSlices());

    for (size_t i = 0; i < re_sample1.numberOfSlices(); ++i) {
        auto mat_1 = re_sample1.avgeSlice(i).refractingMaterial()->rawData();
        auto mat_2 = re_sample2.avgeSlice(i).refractingMaterial()->rawData();
        EXPECT_DOUBLE_EQ(mat_1.real(), mat_2.real());
        EXPECT_DOUBLE_EQ(mat_1.imag(), mat_2.imag());
    }
}
