/**********************************************************************
 
	Copyright (C) 2003 Hirohisa MORI <joshua@nichibun.ac.jp>
 
	This program is free software; you can redistribute it 
	and/or modify it under the terms of the GLOBALBASE 
	Library General Public License (G-LGPL) as published by 

	http://www.globalbase.org/
 
	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.

**********************************************************************/

#include	"xl.h"
#include	"text_render.h"
#include	"tr_lang.h"
#include	"memory_debug.h"
#include	"ex_utils.h"


extern XLISP_ENV * language_env;


L_CHAR *
get_delim_list(XL_SEXP * arg)
{
L_CHAR * delim;
XL_SEXP * d;
int len,_len;
	delim = 0;
	for ( ; get_type(arg) == XLT_PAIR ; arg = cdr(arg) ) {
		d = car(arg);
		if ( get_type(d) != XLT_STRING )
			break;
		_len = l_strlen(d->string.data);
		if ( delim == 0 ) {
			delim = d_alloc(_len*sizeof(L_CHAR));
			len = _len;
		}
		else {
			delim = d_re_alloc(delim,(len + _len)*sizeof(L_CHAR));
			memcpy(&delim[len],d->string.data,_len*sizeof(L_CHAR));
			len += _len;
		}
	}
	if ( delim == 0 )
		return 0;
	delim = d_re_alloc(delim,(len+1)*sizeof(L_CHAR));
	delim[len] = 0;
	return delim;
}

int
cmp_format(L_CHAR * dir,char * cmd)
{
int len;
	len = strlen(cmd);
	if ( memcmp(dir,l_string(std_cm,cmd),len*sizeof(L_CHAR)) )
		return -1;
	switch ( dir[len] ) {
	case ':':
		return len + 1;
	case 0:
		return len;
	default:
		return -1;
	}
}

int
get_writing_dir(L_CHAR * dir)
{
int ret;
int size;
	ret = 0;
	for ( ; dir ; dir += size ) {
		size = cmp_format(dir,"vertical/LtoR");
		if ( size > 0 ) {
			ret |= VSD_V_L2R;
			continue;
		}
		size = cmp_format(dir,"vertical/RtoL");
		if ( size > 0 ) {
			ret |= VSD_V_R2L;
			continue;
		}
		size = cmp_format(dir,"horizontal/LtoR");
		if ( size > 0 ) {
			ret |= VSD_H_L2R;
			continue;
		}
		size = cmp_format(dir,"horizontal/RtoL");
		if ( size > 0 ) {
			ret |= VSD_H_R2L;
			continue;
		}
		return -1;
	}
	return ret;
}


L_CHAR *
ex_option_copy(L_CHAR * org,L_CHAR * delim,L_CHAR * opt)
{
int len,d_len;
	if ( org == 0 )
		goto over_write;
	if ( opt == 0 )
		goto over_write;
	if ( l_strcmp(opt,l_string(std_cm,"add")) == 0 )
		goto add;
	else	goto over_write;
add:
	len = l_strlen(org);
	d_len = l_strlen(delim);
	org = d_re_alloc(org,(len+d_len+1)*sizeof(L_CHAR));
	memcpy(&org[len],delim,(d_len+1)*sizeof(L_CHAR));
	return org;
over_write:
	if ( org )
		d_f_ree(org);
	return ll_copy_str(delim);
}


XL_SEXP *
ex_body(XLISP_ENV * env,XL_SEXP * arg,
	XLISP_ENV * a,
	XL_SYM_FIELD * sf)
{
XLISP_ENV * e;
void * w;
TR_LANG * lang;
XL_SEXP * ret;
	e = new_env(new_env_pair(env,a));
	if ( a->e.work == 0 )
		er_panic("ex_ja");
	lang = a->e.work;
	w = (*lang->get_setup)(lang,0);
	set_env(e,l_string(std_cm,"___work"),get_ptr(w,0));
	for ( arg = cdr(arg) ; get_type(arg) == XLT_PAIR ; arg = cdr(arg) ) {
		ret = eval(e,car(arg));
		if ( get_type(ret) == XLT_ERROR )
			break;
	}
	if ( get_type(ret) != XLT_ERROR ) {
		if ( a->e.work == 0 )
			er_panic("ex_ja");
		lang = a->e.work;
		tr_system_lock();
		(*lang->setup_lang)(lang,TRT_INIT_BIN,w);
		tr_system_unlock();
	}
	(*lang->free_work)(w);
	return ret;
}


