/*
 *
 * Copyright (C) 2007 Google (Evan Stade)
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

#include <stdarg.h>

#include "windef.h"
#include "winbase.h"
#include "wingdi.h"
#include "winnls.h"

#include "objbase.h"

#include "gdiplus.h"
#include "gdiplus_private.h"
#include "wine/debug.h"

WINE_DEFAULT_DEBUG_CHANNEL(gdiplus);

GpStatus WINGDIPAPI GdipCreateStringFormat(INT attr, LANGID lang,
    GpStringFormat **format)
{
    TRACE("(%i, %x, %p)\n", attr, lang, format);

    if(!format)
        return InvalidParameter;

    *format = GdipAlloc(sizeof(GpStringFormat));
    if(!*format)   return OutOfMemory;

    (*format)->attr = attr;
    (*format)->lang = lang;
    (*format)->digitlang = LANG_NEUTRAL;
    (*format)->trimming = StringTrimmingCharacter;
    (*format)->digitsub = StringDigitSubstituteUser;
    (*format)->character_ranges = NULL;
    (*format)->range_count = 0;
    (*format)->generic_typographic = FALSE;
    /* tabstops */
    (*format)->tabcount = 0;
    (*format)->firsttab = 0.0;
    (*format)->tabs = NULL;

    TRACE("<-- %p\n", *format);

    return Ok;
}

GpStatus WINGDIPAPI GdipDeleteStringFormat(GpStringFormat *format)
{
    if(!format)
        return InvalidParameter;

    GdipFree(format->character_ranges);
    GdipFree(format->tabs);
    GdipFree(format);

    return Ok;
}

GpStatus WINGDIPAPI GdipStringFormatGetGenericDefault(GpStringFormat **format)
{
    GpStatus stat;

    if (!format)
        return InvalidParameter;

    stat = GdipCreateStringFormat(0, LANG_NEUTRAL, format);
    if(stat != Ok)
        return stat;

    (*format)->align     = StringAlignmentNear;
    (*format)->vertalign = StringAlignmentNear;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatAlign(GpStringFormat *format,
    StringAlignment *align)
{
    if(!format || !align)
        return InvalidParameter;

    *align = format->align;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatDigitSubstitution(GDIPCONST GpStringFormat *format,
    LANGID *language, StringDigitSubstitute *substitute)
{
    if(!format)
        return InvalidParameter;

    if(language)    *language   = format->digitlang;
    if(substitute)  *substitute = format->digitsub;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatFlags(GDIPCONST GpStringFormat* format,
        INT* flags)
{
    if (!(format && flags))
        return InvalidParameter;

    *flags = format->attr;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatHotkeyPrefix(GDIPCONST GpStringFormat
    *format, INT *hkpx)
{
    if(!format || !hkpx)
        return InvalidParameter;

    *hkpx = (INT)format->hkprefix;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatLineAlign(GpStringFormat *format,
    StringAlignment *align)
{
    if(!format || !align)
        return InvalidParameter;

    *align = format->vertalign;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatMeasurableCharacterRangeCount(
    GDIPCONST GpStringFormat *format, INT *count)
{
    if (!(format && count))
        return InvalidParameter;

    TRACE("%p %p\n", format, count);

    *count = format->range_count;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatTabStopCount(GDIPCONST GpStringFormat *format,
    INT *count)
{
    if(!format || !count)
        return InvalidParameter;

    *count = format->tabcount;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatTabStops(GDIPCONST GpStringFormat *format, INT count,
    REAL *firsttab, REAL *tabs)
{
    if(!format || !firsttab || !tabs)
        return InvalidParameter;

    /* native simply crashes on count < 0 */
    if(count != 0)
        memcpy(tabs, format->tabs, sizeof(REAL)*count);

    *firsttab = format->firsttab;

    return Ok;
}

GpStatus WINGDIPAPI GdipGetStringFormatTrimming(GpStringFormat *format,
    StringTrimming *trimming)
{
    if(!format || !trimming)
        return InvalidParameter;

    *trimming = format->trimming;

    return Ok;
}

GpStatus WINGDIPAPI GdipSetStringFormatAlign(GpStringFormat *format,
    StringAlignment align)
{
    TRACE("(%p, %i)\n", format, align);

    if(!format)
        return InvalidParameter;

    format->align = align;

    return Ok;
}

/*FIXME: digit substitution actually not implemented, get/set only */
GpStatus WINGDIPAPI GdipSetStringFormatDigitSubstitution(GpStringFormat *format,
    LANGID language, StringDigitSubstitute substitute)
{
    TRACE("(%p, %x, %i)\n", format, language, substitute);

    if(!format)
        return InvalidParameter;

    format->digitlang = language;
    format->digitsub  = substitute;

    return Ok;
}

GpStatus WINGDIPAPI GdipSetStringFormatHotkeyPrefix(GpStringFormat *format,
    INT hkpx)
{
    TRACE("(%p, %i)\n", format, hkpx);

    if(!format || hkpx < 0 || hkpx > 2)
        return InvalidParameter;

    format->hkprefix = (HotkeyPrefix) hkpx;

    return Ok;
}

GpStatus WINGDIPAPI GdipSetStringFormatLineAlign(GpStringFormat *format,
    StringAlignment align)
{
    TRACE("(%p, %i)\n", format, align);

    if(!format)
        return InvalidParameter;

    format->vertalign = align;

    return Ok;
}

GpStatus WINGDIPAPI GdipSetStringFormatMeasurableCharacterRanges(
    GpStringFormat *format, INT rangeCount, GDIPCONST CharacterRange *ranges)
{
    CharacterRange *new_ranges;

    if (!(format && ranges))
        return InvalidParameter;

    TRACE("%p, %d, %p\n", format, rangeCount, ranges);

    new_ranges = GdipAlloc(rangeCount * sizeof(CharacterRange));
    if (!new_ranges)
        return OutOfMemory;

    GdipFree(format->character_ranges);
    format->character_ranges = new_ranges;
    memcpy(format->character_ranges, ranges, sizeof(CharacterRange) * rangeCount);
    format->range_count = rangeCount;

    return Ok;
}

GpStatus WINGDIPAPI GdipSetStringFormatTabStops(GpStringFormat *format, REAL firsttab,
    INT count, GDIPCONST REAL *tabs)
{
    TRACE("(%p, %0.2f, %i, %p)\n", format, firsttab, count, tabs);

    if(!format || !tabs)
        return InvalidParameter;

    if(count > 0){
        if(firsttab < 0.0)  return NotImplemented;
        /* first time allocation */
        if(format->tabcount == 0){
            format->tabs = GdipAlloc(sizeof(REAL)*count);
            if(!format->tabs)
                return OutOfMemory;
        }
        /* reallocation */
        if((format->tabcount < count) && (format->tabcount > 0)){
            REAL *ptr;
            ptr = HeapReAlloc(GetProcessHeap(), 0, format->tabs, sizeof(REAL)*count);
            if(!ptr)
                return OutOfMemory;
            format->tabs = ptr;
        }
        format->firsttab = firsttab;
        format->tabcount = count;
        memcpy(format->tabs, tabs, sizeof(REAL)*count);
    }

    return Ok;
}

GpStatus WINGDIPAPI GdipSetStringFormatTrimming(GpStringFormat *format,
    StringTrimming trimming)
{
    TRACE("(%p, %i)\n", format, trimming);

    if(!format)
        return InvalidParameter;

    format->trimming = trimming;

    return Ok;
}

GpStatus WINGDIPAPI GdipSetStringFormatFlags(GpStringFormat *format, INT flags)
{
    TRACE("(%p, %x)\n", format, flags);

    if(!format)
        return InvalidParameter;

    format->attr = flags;

    return Ok;
}

GpStatus WINGDIPAPI GdipCloneStringFormat(GDIPCONST GpStringFormat *format, GpStringFormat **newFormat)
{
    if(!format || !newFormat)
        return InvalidParameter;

    *newFormat = GdipAlloc(sizeof(GpStringFormat));
    if(!*newFormat)    return OutOfMemory;

    **newFormat = *format;

    if(format->tabcount > 0){
        (*newFormat)->tabs = GdipAlloc(sizeof(REAL) * format->tabcount);
        if(!(*newFormat)->tabs){
            GdipFree(*newFormat);
            return OutOfMemory;
        }
        memcpy((*newFormat)->tabs, format->tabs, sizeof(REAL) * format->tabcount);
    }
    else
        (*newFormat)->tabs = NULL;

    if(format->range_count > 0){
        (*newFormat)->character_ranges = GdipAlloc(sizeof(CharacterRange) * format->range_count);
        if(!(*newFormat)->character_ranges){
            GdipFree((*newFormat)->tabs);
            GdipFree(*newFormat);
            return OutOfMemory;
        }
        memcpy((*newFormat)->character_ranges, format->character_ranges,
               sizeof(CharacterRange) * format->range_count);
    }
    else
        (*newFormat)->character_ranges = NULL;

    TRACE("%p %p\n",format,newFormat);

    return Ok;
}

GpStatus WINGDIPAPI GdipStringFormatGetGenericTypographic(GpStringFormat **format)
{
    GpStatus stat;

    if(!format)
        return InvalidParameter;

    stat = GdipCreateStringFormat(StringFormatFlagsNoFitBlackBox |
                                  StringFormatFlagsLineLimit |
                                  StringFormatFlagsNoClip, LANG_NEUTRAL, format);
    if(stat != Ok)
        return stat;

    (*format)->digitlang = LANG_NEUTRAL;
    (*format)->digitsub  = StringDigitSubstituteUser;
    (*format)->trimming  = StringTrimmingNone;
    (*format)->hkprefix  = HotkeyPrefixNone;
    (*format)->align     = StringAlignmentNear;
    (*format)->vertalign = StringAlignmentNear;
    (*format)->generic_typographic = TRUE;

    TRACE("%p => %p\n", format, *format);

    return Ok;
}
