/*
 *
 * UNICON - The Console Chinese & I18N
 * Copyright (c) 1999-2002
 *
 * This file is part of UNICON, a console Chinese & I18N
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program 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 General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 *
 * See the file COPYING directory of this archive
 * Author: see CREDITS
 */

#include <stdio.h>
#include <newt.h>

#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdlib.h>
#include <sys/ioctl.h>
#include <fcntl.h>
#include <ctype.h>
#include <sys/time.h>
#include <errno.h>
#include <signal.h>
#if (__GNU_LIBRARY__ >= 6)
#include <sys/perm.h>
#else
#include <linux/types.h>
#include <linux/termios.h>
#endif
#include <linux/vt.h>
#include <termios.h>
#include <locale.h>

#include "unikey.h"

#define  MAX_LANG         5
#define NEWT_KEY_ESC '\033'

/* font_type */
#define XL_DB_GB       0
#define XL_DB_BIG5     1
#define XL_DB_JIS      2
#define XL_DB_KSCM     3
#define XL_DB_GBK      4

typedef struct menuAction_T
{
    char *name;
}
menuAction;

int inputmethod_notify = 0, lang = 0;
static char *menuLangs[MAX_LANG] =
{
    "GB",
    "BIG5",
    "JIS",
    "KSCM",
    "GBK",
};

#define OK                1
#define CANCEL            0
int DoLangSelection ()
{
    newtComponent mAnswer, form, checkbox, rb[MAX_LANG], ok, cancel;
    struct newtExitStruct cevent;
    char cbValue;
    int i, reason;

    inputmethod_notify = 0;
    lang = 0;

    newtInit();
    newtCls();

    newtOpenWindow(10, 5, 40, MAX_LANG + 8, "Unicon Configuration V 0.1");

    checkbox = newtCheckbox(1, 1, "Change Input Method", ' ', " X", &cbValue);

    rb[0] = newtRadiobutton(1, 3, menuLangs[0], 1, NULL);
    for (i = 1; i < MAX_LANG; i++)
        rb[i] = newtRadiobutton(1, 3 + i, menuLangs[i], 0, rb[i-1]);

    ok = newtButton(1, 4 + MAX_LANG, "Ok");
    cancel = newtButton(12, 4 + MAX_LANG, "Cancel");

    form = newtForm(NULL, NULL, 0);
    newtFormAddComponent(form, checkbox);
    for (i = 0; i < MAX_LANG; i++)
        newtFormAddComponent(form, rb[i]);
    newtFormAddComponent(form, ok);
    newtFormAddComponent(form, cancel);

    newtFormAddHotKey (form, NEWT_KEY_ESC);
    newtFormRun(form, &cevent);
    newtFinished();

    mAnswer=newtFormGetCurrent (form);
    if (mAnswer == ok)
        reason = OK;
    else
        reason = CANCEL;

    if (reason == CANCEL)
        return 0;

    /* We cannot destroy the form until after we've found the current
       radio button */

    for (i = 1; i < MAX_LANG; i++)
        if (newtRadioGetCurrent(rb[0]) == rb[i])
            lang = i;
    newtFormDestroy(form);

    /* But the checkbox's value is stored locally */
    if (cbValue == 'X')
        inputmethod_notify = 1;
    return 1;
}

void ChangeLocale (int coding)
{
    switch (coding)
    {
        case XL_DB_GB:
            setlocale (LC_ALL, "zh_CN.GBK");
            break;
        case XL_DB_BIG5:
            setlocale (LC_ALL, "zh_CN.Big5");
            break;
        case XL_DB_JIS:
            break;
        case XL_DB_KSCM:
            break;
        case XL_DB_GBK:
            setlocale (LC_ALL, "zh_CN.GBK");
            break;
    }
}

//only get the current tty no.
int GetCurrentTTY ()
{
   int fd;
   struct vt_stat vs;

   fd = open("/dev/tty0", O_RDONLY);
   if(ioctl(fd, VT_GETSTATE, &vs) == -1){
      printf("Error get status.\n");
      exit(1);
   }
   close(fd);
   return vs.v_active - 1;
}

void ChangeCurrentTtyFont (int tty, int coding, int inputmethod_notify)
{
    int file_desc = open ("/dev/unikey", 0);
    VtFont_T aa;
    int ret_val;

    if (file_desc < 0) {
        printf ("Can't open device file: %s\n", DEVICE_FILE_NAME);
        exit(-1);
    }

    aa.tty = tty;
    aa.font_type = coding;
    aa.input_method_notify = inputmethod_notify;
    ret_val = ioctl(file_desc, UNI_SET_CURRENT_FONT, &aa);

    if (ret_val < 0) {
        printf ("Set Current Font failed.\n");
        exit(-1);
    }
    close(file_desc);
}

int TestFontExist (int coding)
{
    switch (coding)
    {
        case XL_DB_GB:
        case XL_DB_BIG5:
        case XL_DB_JIS:
        case XL_DB_KSCM:
        case XL_DB_GBK:
    }
    return 1;
}

#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netdb.h>
#include <sys/ipc.h>
#include <sys/sem.h>

#define IPPORT_LICENSE               8888

static void DoSendToServer (void *buf, int len)
{
    int                     sockfd;
    struct sockaddr_in      name;
    int                     opt = 1;
    int                     i;
    static int              port = IPPORT_LICENSE;

    printf ("DoSendToServer (buf = 0x%x, len = %d)\n", (long) buf, len);
    sockfd = socket(PF_INET, SOCK_DGRAM, 0);
    setsockopt (sockfd, SOL_SOCKET, SO_BROADCAST, &opt, sizeof(opt));

    name.sin_family = PF_INET;
    name.sin_addr.s_addr = INADDR_BROADCAST;
    name.sin_port = htons(port++);

    sendto (sockfd, buf, len, 0, (struct sockaddr *) &name, sizeof(name));

    close(sockfd);
}

typedef struct __UniconCfg_T__
{
    int tty;
    int coding;
    int input_method_notify;
} UniconCfg_T;

void NotifyServer (int tty, int coding)
{
    UniconCfg_T aa;
    aa.tty = tty;
    aa.coding = coding;
    printf ("DoSendToServer () \n");
    DoSendToServer (&aa, sizeof (aa));
}

void Usages (char *name)
{
    printf ("%s [--gb | --big5 | --gbk | --kscm | --jis \n", name);
    printf ("   [--notify_input_method]] \n");
    printf ("   [--tty 1-6] \n");
    exit (0);
}

int main (int argc, char **argv)
{
    int i, coding_int = XL_DB_GB;
    int tty;

    tty = GetCurrentTTY ();
    if (argc == 1)
    {
        if (DoLangSelection () == 1)
        {
             if (TestFontExist (lang) == 0)
                 printf ("font does not exist\n"); 
             else
             {
                 ChangeLocale (lang);
                 ChangeCurrentTtyFont (tty, lang, inputmethod_notify);
             }
        }
        // printf ("tty=%d, lang=%d, inputmethod_notify=%d\n", 
        //        tty, lang, inputmethod_notify);
        return 0;
    }

    i = 0;
    while (--argc > 0)
    {
        i ++;
        if (argv[i] == NULL)
            break;
        if (strcmp (argv[i], "--gb") == 0)
            coding_int = XL_DB_GB;
        else if (strcmp (argv[i], "--gbk") == 0)
            coding_int = XL_DB_GBK;
        else if (strcmp (argv[i], "--big5") == 0)
            coding_int = XL_DB_BIG5;
        else if (strcmp (argv[i], "--jis") == 0)
            coding_int = XL_DB_JIS;
        else if (strcmp (argv[i], "--kscm") == 0)
            coding_int = XL_DB_KSCM;
        else if (strcmp (argv[i], "--notify_input_method") == 0)
            inputmethod_notify = 1;
        else if (strcmp (argv[i], "--tty") == 0)
        {
            tty = atoi (argv[i + 1]) - 1;
            i ++;
        }
        else
            Usages (argv[0]);
    }
    ChangeLocale (coding_int);
    ChangeCurrentTtyFont (tty, coding_int, inputmethod_notify);
    return 0;
}

