// Copyright 2023 The Tint Authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

////////////////////////////////////////////////////////////////////////////////
// File generated by 'tools/src/cmd/gen' using the template:
//   src/tint/lang/core/interpolation_sampling_test.cc.tmpl
//
// To regenerate run: './tools/run gen'
//
//                       Do not modify this file directly
////////////////////////////////////////////////////////////////////////////////

#include "src/tint/lang/core/interpolation_sampling.h"

#include <gtest/gtest.h>
#include <string>

#include "src/tint/utils/text/string.h"

namespace tint::core {
namespace {

namespace interpolation_sampling_tests {

namespace parse_print_tests {

struct Case {
    const char* string;
    InterpolationSampling value;
};

inline std::ostream& operator<<(std::ostream& out, Case c) {
    return out << "'" << std::string(c.string) << "'";
}

static constexpr Case kValidCases[] = {
    {"center", InterpolationSampling::kCenter},
    {"centroid", InterpolationSampling::kCentroid},
    {"sample", InterpolationSampling::kSample},
};

static constexpr Case kInvalidCases[] = {
    {"ccnter", InterpolationSampling::kUndefined},
    {"c3r", InterpolationSampling::kUndefined},
    {"centeV", InterpolationSampling::kUndefined},
    {"1entroid", InterpolationSampling::kUndefined},
    {"enJrqqid", InterpolationSampling::kUndefined},
    {"llen77roid", InterpolationSampling::kUndefined},
    {"sapppHHe", InterpolationSampling::kUndefined},
    {"cam", InterpolationSampling::kUndefined},
    {"sbGpl", InterpolationSampling::kUndefined},
};

using InterpolationSamplingParseTest = testing::TestWithParam<Case>;

TEST_P(InterpolationSamplingParseTest, Parse) {
    const char* string = GetParam().string;
    InterpolationSampling expect = GetParam().value;
    EXPECT_EQ(expect, ParseInterpolationSampling(string));
}

INSTANTIATE_TEST_SUITE_P(ValidCases,
                         InterpolationSamplingParseTest,
                         testing::ValuesIn(kValidCases));
INSTANTIATE_TEST_SUITE_P(InvalidCases,
                         InterpolationSamplingParseTest,
                         testing::ValuesIn(kInvalidCases));

using InterpolationSamplingPrintTest = testing::TestWithParam<Case>;

TEST_P(InterpolationSamplingPrintTest, Print) {
    InterpolationSampling value = GetParam().value;
    const char* expect = GetParam().string;
    EXPECT_EQ(expect, tint::ToString(value));
}

INSTANTIATE_TEST_SUITE_P(ValidCases,
                         InterpolationSamplingPrintTest,
                         testing::ValuesIn(kValidCases));

}  // namespace parse_print_tests

}  // namespace interpolation_sampling_tests

}  // namespace
}  // namespace tint::core
