/*
**********************************************************************
*   Copyright (c) 2000, International Business Machines
*   Corporation and others.  All Rights Reserved.
**********************************************************************
*   Date        Name        Description
*   01/17/2000  aliu        Ported from Java.
**********************************************************************
*/
#include "unicode/jamohang.h"
#include "unicode/rep.h"
#include "unicode/unifilt.h"
#include "unicode/unicode.h"

/**
 * ID for this transliterator.
 */
const char* JamoHangulTransliterator::_ID = "Jamo-Hangul";

/**
 * Constructs a transliterator.
 */
JamoHangulTransliterator::JamoHangulTransliterator(UnicodeFilter* adoptedFilter) :
    Transliterator(_ID, adoptedFilter) {
    setMaximumContextLength(3);
}

/**
 * Copy constructor.
 */
JamoHangulTransliterator::JamoHangulTransliterator(const JamoHangulTransliterator& o) :
    Transliterator(o) {
}

/**
 * Assignment operator.
 */
JamoHangulTransliterator& JamoHangulTransliterator::operator=(
                                             const JamoHangulTransliterator& o) {
    Transliterator::operator=(o);
    return *this;
}

/**
 * Transliterator API.
 */
Transliterator* JamoHangulTransliterator::clone(void) const {
    return new JamoHangulTransliterator(*this);
}

/**
 * Implements {@link Transliterator#handleTransliterate}.
 */
void JamoHangulTransliterator::handleTransliterate(Replaceable& text, Position& offsets,
                                                   UBool isIncremental) const {
    /**
     * Performs transliteration changing Jamo to Hangul 
     */
    int32_t cursor = offsets.cursor;
    int32_t limit = offsets.limit;
    if (cursor >= limit) return;

    int32_t count;

    UChar last = filteredCharAt(text, cursor++);
    UnicodeString str("a", 1);
    while (cursor <= limit) {
        UChar next = 0xFFFF; // go over end of string, just in case
        if (cursor < limit) next = filteredCharAt(text, cursor);
        UChar replacement = composeHangul(last, next, count);
        if (replacement != last) {
            str[0] = replacement;
            text.handleReplaceBetween(cursor-1, cursor-1 + count, str);
            limit = limit - count + 1; // fix up limit 2 => -1, 1 => 0
            last = replacement;
            if (next == 0xFFFF) break;
            // don't change cursor, so we revisit char
        } else {
            ++cursor;
            last = next;
        }
    }

    offsets.limit = limit + 1;
    offsets.cursor = cursor;
}

// These constants are from the Unicode book's algorithm.

#define SBase   (0xAC00)
#define LBase   (0x1100)
#define VBase   (0x1161)
#define TBase   (0x11A7)
#define LCount  (19)
#define VCount  (21)
#define TCount  (28)
#define NCount  (VCount * TCount)   // 588
#define SCount  (LCount * NCount)   // 11172
#define LLimit  (0x1200)

/**
 * Return composed character (if it is a modern jamo)
 * last otherwise.
 * If there is a replacement, returns count[0] = 2 if ch was used, 1 otherwise
 */
UChar JamoHangulTransliterator::composeHangul(UChar last, UChar ch, int32_t& count) {
    count = 2; // default is replace 2 chars
    // check to see if two current characters are L and V
    int32_t LIndex = last - LBase;
    if (0 <= LIndex && LIndex < LCount) {
        int32_t VIndex = ch - VBase;
        if (0 <= VIndex && VIndex < VCount) {
            // make syllable of form LV
            return (UChar)(SBase + (LIndex * VCount + VIndex) * TCount);
        } else {
            // it is isolated, so fix!
            count = 1; // not using ch
            return (UChar)(SBase + (LIndex * VCount) * TCount);
        }
    }
      
    // if neither case was true, see if we have an isolated Jamo we need to fix
    if (LBase <= last && last < LLimit) {
        // need to fix: it is either medial or final!
        int32_t VIndex = last - VBase;
        if (0 <= VIndex && VIndex < VCount) {
            LIndex = 0x110B - LBase; // use empty consonant
            // make syllable of form LV
            count = 1; // not using ch
            return (UChar)(SBase + (LIndex * VCount + VIndex) * TCount);
        }
        // ok, see if final. Use null consonant + a + final
        int32_t TIndex = last - TBase;
        if (0 <= TIndex && TIndex <= TCount) {  // need to fix!
            count = 1; // not using ch
            return (UChar)(0xC544 + TIndex);
        }
    }
 
    // check to see if two current characters are LV and T
    int32_t SIndex = last - SBase;
    if (0 <= SIndex && SIndex < SCount && (SIndex % TCount) == 0) {
        int32_t TIndex = ch - TBase;
        if (0 <= TIndex && TIndex <= TCount) {
            // make syllable of form LVT
            return (UChar)(last + TIndex);
        }
    }
      
    return last;
}    
