// Copyright 2014 PDFium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com

#include "../../../include/fxge/fx_ge.h"
#include "../agg/include/fx_agg_driver.h"
#include "text_int.h"

#if _FXM_PLATFORM_ == _FXM_PLATFORM_LINUX_
static const struct {
    const FX_CHAR*	m_pName;
    const FX_CHAR*	m_pSubstName;
}
Base14Substs[] = {
    {"Courier", "Courier New"},
    {"Courier-Bold", "Courier New Bold"},
    {"Courier-BoldOblique", "Courier New Bold Italic"},
    {"Courier-Oblique", "Courier New Italic"},
    {"Helvetica", "Arial"},
    {"Helvetica-Bold", "Arial Bold"},
    {"Helvetica-BoldOblique", "Arial Bold Italic"},
    {"Helvetica-Oblique", "Arial Italic"},
    {"Times-Roman", "Times New Roman"},
    {"Times-Bold", "Times New Roman Bold"},
    {"Times-BoldItalic", "Times New Roman Bold Italic"},
    {"Times-Italic", "Times New Roman Italic"},
};
class CFX_LinuxFontInfo : public CFX_FolderFontInfo
{
public:
    virtual void*		MapFont(int weight, FX_BOOL bItalic, int charset, int pitch_family, const FX_CHAR* family, FX_BOOL& bExact);
    FX_BOOL				ParseFontCfg();
    void*				FindFont(int weight, FX_BOOL bItalic, int charset, int pitch_family, const FX_CHAR* family, FX_BOOL bMatchName);
};
#define LINUX_GPNAMESIZE	6
static const struct {
    const FX_CHAR* NameArr[LINUX_GPNAMESIZE];
}
LinuxGpFontList[] = {
    {{"TakaoPGothic", "VL PGothic", "IPAPGothic", "VL Gothic", "Kochi Gothic", "VL Gothic regular"}},
    {{"TakaoGothic", "VL Gothic", "IPAGothic", "Kochi Gothic", NULL, "VL Gothic regular"}},
    {{"TakaoPMincho", "IPAPMincho", "VL Gothic", "Kochi Mincho", NULL, "VL Gothic regular"}},
    {{"TakaoMincho", "IPAMincho", "VL Gothic", "Kochi Mincho", NULL, "VL Gothic regular"}},
};
static const FX_CHAR* const g_LinuxGbFontList[] = {
    "AR PL UMing CN Light",
    "WenQuanYi Micro Hei",
    "AR PL UKai CN",
};
static const FX_CHAR* const g_LinuxB5FontList[] = {
    "AR PL UMing TW Light",
    "WenQuanYi Micro Hei",
    "AR PL UKai TW",
};
static const FX_CHAR* const g_LinuxHGFontList[] = {
    "UnDotum",
};
static int32_t GetJapanesePreference(const FX_CHAR* facearr, int weight, int picth_family)
{
    CFX_ByteString face = facearr;
    if (face.Find("Gothic") >= 0 || face.Find("\x83\x53\x83\x56\x83\x62\x83\x4e") >= 0) {
        if (face.Find("PGothic") >= 0 || face.Find("\x82\x6f\x83\x53\x83\x56\x83\x62\x83\x4e") >= 0) {
            return 0;
        } else {
            return 1;
        }
    } else if (face.Find("Mincho") >= 0 || face.Find("\x96\xbe\x92\xa9") >= 0) {
        if (face.Find("PMincho") >= 0 || face.Find("\x82\x6f\x96\xbe\x92\xa9") >= 0) {
            return 2;
        } else {
            return 3;
        }
    }
    if (!(picth_family & FXFONT_FF_ROMAN) && weight > 400) {
        return 0;
    }
    return 2;
}
void* CFX_LinuxFontInfo::MapFont(int weight, FX_BOOL bItalic, int charset, int pitch_family, const FX_CHAR* cstr_face, FX_BOOL& bExact)
{
    CFX_ByteString face = cstr_face;
    int iBaseFont;
    for (iBaseFont = 0; iBaseFont < 12; iBaseFont ++)
        if (face == CFX_ByteStringC(Base14Substs[iBaseFont].m_pName)) {
            face = Base14Substs[iBaseFont].m_pSubstName;
            bExact = TRUE;
            break;
        }
    if (iBaseFont < 12) {
        return GetFont(face);
    }
    void* p = NULL;
    FX_BOOL bCJK = TRUE;
    switch (charset) {
        case FXFONT_SHIFTJIS_CHARSET: {
                int32_t index = GetJapanesePreference(cstr_face, weight, pitch_family);
                if (index < 0) {
                    break;
                }
                for (int32_t i = 0; i < LINUX_GPNAMESIZE; i++)
                    if (m_FontList.Lookup(LinuxGpFontList[index].NameArr[i], p)) {
                        return p;
                    }
            }
            break;
        case FXFONT_GB2312_CHARSET: {
                static int32_t s_gbCount = sizeof(g_LinuxGbFontList) / sizeof(const FX_CHAR*);
                for (int32_t i = 0; i < s_gbCount; i++)
                    if (m_FontList.Lookup(g_LinuxGbFontList[i], p)) {
                        return p;
                    }
            }
            break;
        case FXFONT_CHINESEBIG5_CHARSET: {
                static int32_t s_b5Count = sizeof(g_LinuxB5FontList) / sizeof(const FX_CHAR*);
                for (int32_t i = 0; i < s_b5Count; i++)
                    if (m_FontList.Lookup(g_LinuxB5FontList[i], p)) {
                        return p;
                    }
            }
            break;
        case FXFONT_HANGEUL_CHARSET: {
                static int32_t s_hgCount = sizeof(g_LinuxHGFontList) / sizeof(const FX_CHAR*);
                for (int32_t i = 0; i < s_hgCount; i++)
                    if (m_FontList.Lookup(g_LinuxHGFontList[i], p)) {
                        return p;
                    }
            }
            break;
        default:
            bCJK = FALSE;
            break;
    }
    if (charset == FXFONT_ANSI_CHARSET && (pitch_family & FXFONT_FF_FIXEDPITCH)) {
        return GetFont("Courier New");
    }
    return FindFont(weight, bItalic, charset, pitch_family, cstr_face, !bCJK);
}
static FX_DWORD _LinuxGetCharset(int charset)
{
    switch(charset) {
        case FXFONT_SHIFTJIS_CHARSET:
            return CHARSET_FLAG_SHIFTJIS;
        case FXFONT_GB2312_CHARSET:
            return CHARSET_FLAG_GB;
        case FXFONT_CHINESEBIG5_CHARSET:
            return CHARSET_FLAG_BIG5;
        case FXFONT_HANGEUL_CHARSET:
            return CHARSET_FLAG_KOREAN;
        case FXFONT_SYMBOL_CHARSET:
            return CHARSET_FLAG_SYMBOL;
        case FXFONT_ANSI_CHARSET:
            return CHARSET_FLAG_ANSI;
        default:
            break;
    }
    return 0;
}
static int32_t _LinuxGetSimilarValue(int weight, FX_BOOL bItalic, int pitch_family, FX_DWORD style)
{
    int32_t iSimilarValue = 0;
    if ((style & FXFONT_BOLD) == (weight > 400)) {
        iSimilarValue += 16;
    }
    if ((style & FXFONT_ITALIC) == bItalic) {
        iSimilarValue += 16;
    }
    if ((style & FXFONT_SERIF) == (pitch_family & FXFONT_FF_ROMAN)) {
        iSimilarValue += 16;
    }
    if ((style & FXFONT_SCRIPT) == (pitch_family & FXFONT_FF_SCRIPT)) {
        iSimilarValue += 8;
    }
    if ((style & FXFONT_FIXED_PITCH) == (pitch_family & FXFONT_FF_FIXEDPITCH)) {
        iSimilarValue += 8;
    }
    return iSimilarValue;
}
void* CFX_LinuxFontInfo::FindFont(int weight, FX_BOOL bItalic, int charset, int pitch_family, const FX_CHAR* family, FX_BOOL bMatchName)
{
    CFontFaceInfo* pFind = NULL;
    FX_DWORD charset_flag = _LinuxGetCharset(charset);
    int32_t iBestSimilar = 0;
    FX_POSITION pos = m_FontList.GetStartPosition();
    while (pos) {
        CFX_ByteString bsName;
        CFontFaceInfo* pFont = NULL;
        m_FontList.GetNextAssoc(pos, bsName, (void*&)pFont);
        if (!(pFont->m_Charsets & charset_flag) && charset != FXFONT_DEFAULT_CHARSET) {
            continue;
        }
        int32_t iSimilarValue = 0;
        int32_t index = bsName.Find(family);
        if (bMatchName && index < 0) {
            continue;
        }
        if (!bMatchName && index > 0) {
            iSimilarValue += 64;
        }
        iSimilarValue = _LinuxGetSimilarValue(weight, bItalic, pitch_family, pFont->m_Styles);
        if (iSimilarValue > iBestSimilar) {
            iBestSimilar = iSimilarValue;
            pFind = pFont;
        }
    }
    return pFind;
}
IFX_SystemFontInfo* IFX_SystemFontInfo::CreateDefault()
{
    CFX_LinuxFontInfo* pInfo = new CFX_LinuxFontInfo;
    if (!pInfo->ParseFontCfg()) {
        pInfo->AddPath("/usr/share/fonts");
        pInfo->AddPath("/usr/share/X11/fonts/Type1");
        pInfo->AddPath("/usr/share/X11/fonts/TTF");
        pInfo->AddPath("/usr/local/share/fonts");
    }
    return pInfo;
}
FX_BOOL CFX_LinuxFontInfo::ParseFontCfg()
{
    return FALSE;
}
void CFX_GEModule::InitPlatform()
{
    m_pFontMgr->SetSystemFontInfo(IFX_SystemFontInfo::CreateDefault());
}
void CFX_GEModule::DestroyPlatform()
{
}
#endif  // _FXM_PLATFORM_ == _FXM_PLATFORM_LINUX_
