// © 2016 and later: Unicode, Inc. and others.
// License & terms of use: http://www.unicode.org/copyright.html
/*
 *******************************************************************************
 * Copyright (C) 2003-2012, Google, International Business Machines Corporation and    *
 * others. All Rights Reserved.                                                *
 *******************************************************************************
*/
package com.ibm.icu.dev.test.util;

import java.util.Arrays;
import java.util.List;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;

import com.ibm.icu.dev.test.TestFmwk;
import com.ibm.icu.util.GenderInfo;
import com.ibm.icu.util.GenderInfo.Gender;
import com.ibm.icu.util.ULocale;

@RunWith(JUnit4.class)
public class GenderInfoTest extends TestFmwk {
    public static GenderInfo NEUTRAL_LOCALE = GenderInfo.getInstance(ULocale.ENGLISH);
    public static GenderInfo MIXED_NEUTRAL_LOCALE = GenderInfo.getInstance(new ULocale("is"));
    public static GenderInfo MALE_TAINTS_LOCALE = GenderInfo.getInstance(ULocale.FRENCH);

    @Test
    public void TestEmpty() {
        // Gender of the empty list is always OTHER regardless of gender style.
        check(Gender.OTHER, Gender.OTHER, Gender.OTHER);
    }

    @Test
    public void TestOne() {
        // Gender of single item list is always gender of sole item regardless of
        // gender style.
        for (Gender g : Gender.values()) {
            check(g, g, g, g);
        }
    }

    @Test
    public void TestOther() {
        check(Gender.OTHER, Gender.MALE, Gender.MALE, Gender.MALE, Gender.MALE);
        check(Gender.OTHER, Gender.OTHER, Gender.MALE, Gender.MALE, Gender.FEMALE);
        check(Gender.OTHER, Gender.OTHER, Gender.MALE, Gender.MALE, Gender.OTHER);

        check(Gender.OTHER, Gender.OTHER, Gender.MALE, Gender.FEMALE, Gender.MALE);
        check(Gender.OTHER, Gender.FEMALE, Gender.FEMALE, Gender.FEMALE, Gender.FEMALE);
        check(Gender.OTHER, Gender.OTHER, Gender.MALE, Gender.FEMALE, Gender.OTHER);

        check(Gender.OTHER, Gender.OTHER, Gender.MALE, Gender.OTHER, Gender.MALE);
        check(Gender.OTHER, Gender.OTHER, Gender.MALE, Gender.OTHER, Gender.FEMALE);
        check(Gender.OTHER, Gender.OTHER, Gender.MALE, Gender.OTHER, Gender.OTHER);
    }

    public void check(Gender neutral, Gender mixed, Gender taints, Gender... genders) {
        List<Gender> mixed0 = Arrays.asList(genders);
        assertEquals("neutral " + mixed0, neutral, NEUTRAL_LOCALE.getListGender(mixed0));
        assertEquals("mixed neutral " + mixed0, mixed, MIXED_NEUTRAL_LOCALE.getListGender(mixed0));
        assertEquals("male taints " + mixed0, taints, MALE_TAINTS_LOCALE.getListGender(mixed0));
    }

    @Test
    public void TestFallback() {
        assertEquals("Strange locale = root", GenderInfo.getInstance(ULocale.ROOT), GenderInfo.getInstance(new ULocale("xxx")));
        assertEquals("Strange locale = root", GenderInfo.getInstance(ULocale.FRANCE), GenderInfo.getInstance(ULocale.CANADA_FRENCH));
    }
}
