/********************************************************************
This file is part of the abs 0.907 distribution.  abs is a spreadsheet
with graphical user interface.

Copyright (C) 1998-2001  André Bertin (Andre.Bertin@ping.be) 

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 if in the same spirit as version 2.

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.

Concact: abs@pi.be
         http://home.pi.be/bertin/abs.shtml

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



























#include "workbook.h"
#include "style.h"
#include "memory.h"
#include "project.h"
#include <stdio.h>

static int nworkbook = 1;

Workbook *ActiveWorkbook;


Workbook *
newworkbook (filename)
     char *filename;
{
  int i;
  Workbook *workbook;
  absstartmap ();
  workbook = (Workbook *) absmalloc (sizeof (Workbook), "newworkbook:workbook ");
  if (workbook == NULL)
    fprintf (stderr, "workbook not allocated!");

  workbook->nbworksheet = 3;

  workbook->Worksheets =
    (Worksheet **) absmalloc (sizeof (Worksheet *) * 3, "newworkbook:workbook->Worksheets ");

  ActiveWorkbook = workbook;
  for (i = 0; i < 3; i++)
    {
      workbook->Worksheets[i] = newworksheet ();
      workbook->Worksheets[i]->Name[0] = 'A' + i;
      workbook->Worksheets[i]->Name[1] = '\0';
    }

  workbook->activeworksheet = workbook->Worksheets[0];

  workbook->style = newstyle (STY_DEF_CELL);
  workbook_setnormalstyle (workbook);


  workbook->project = new_project ();

  workbook->name = (char *) absmalloc (sizeof (char) * (strlen (filename) + 1), "newworkbook:workbook->name ");
  strcpy (workbook->name, filename);
  workbook->first_vis_wks = 0;
  workbook->objnum = nworkbook++;
  
  
  
  
  return workbook;
}

Workbook *
newworkbook1 (nb)
     int nb;
{
  Workbook *workbook;
  workbook = (Workbook *) absmalloc (sizeof (Workbook), "newworkbook1:workbook ");

  workbook->nbworksheet = nb;

  if (nb > 0)
    {
      workbook->Worksheets =
	(Worksheet **) absmalloc (sizeof (Worksheet *) * nb, "newworkbook1:workbook->Worksheets ");

    }
  if (workbook == NULL)
    fprintf (stderr, "workbook not allocated!");

  workbook->style = newstyle (STY_CELL);
  workbook_setnormalstyle (workbook);

  workbook->project = new_project ();
  workbook->objnum = nworkbook++;
  workbook->first_vis_wks = 0;
  
  return workbook;
}

int
freeworkbook (workbook)
     Workbook *workbook;
{
  int i;
  if (workbook == NULL)
    return 1;
  
  for (i = 0; i < workbook->nbworksheet; i++)
    {
      freeworksheet (workbook->Worksheets[i]);
    }
  absfree (workbook->Worksheets, "freeworkbook:workbook->Worksheets ");
  
  freeproject (workbook->project);


  freestyle (workbook->style);
  absfree (workbook->name, "freeworkbook:workbook->name ");
  absfree (workbook, "freeworkbook:workbook ");

  absmemmap ();
  return 0;
}

int
workbook_setnormalstyle (workbook)
     Workbook *workbook;
{
  setstyle (workbook->style, STY_FG, 6);
  setstyle (workbook->style, STY_BG, 45);
  setstyle (workbook->style, STY_BORDER_TOP, 0);
  setstyle (workbook->style, STY_BORDER_BOT, 0);
  setstyle (workbook->style, STY_BORDER_RIG, 0);
  setstyle (workbook->style, STY_BORDER_LEF, 0);
  setstyle (workbook->style, STY_FORMAT, 1);
  setstyle (workbook->style, STY_DECIMAL, 0);
  setstyle (workbook->style, STY_JUSTIF, 2);
  setstyle (workbook->style, STY_FONT, 2);
  setstyle (workbook->style, STY_FONTW, 0);
  setstyle (workbook->style, STY_FONTS, 2);
  return 0;
}

Workbook *
workbook_open (filename)
     char *filename;
{
  return NULL;
}

int
workbook_save (workbook, filename)
     Workbook *workbook;
     char *filename;
{				
  int i;
  int active = 0;
  FILE *fp = fopen (filename, "w");
  if (fp == NULL)
    return -1;
  

  if (strcmp (filename, workbook->name))
    {
      absfree (workbook->name, "workbook_save:workbook->name ");
      workbook->name = (char *) absmalloc (sizeof (char) * (strlen (filename) + 1), "workbook_save:workbook->name ");
      strcpy (workbook->name, filename);
    }

  if (!labelexist (workbook->project, "main"))
    {
      fprintf (fp, "Sub main()\n");
      fprintf (fp, "'you can edit this macro to execute any command when loading this workbook\n");
      fprintf (fp, "'next line call the routine that fill the sheet\n");
      fprintf (fp, "call absmain()\n");
      fprintf (fp, "End Sub\n");
    }

  project_save (workbook->project, fp);

  fprintf (fp, "\n'Function not used if run inside abs (replaced by a builtin function)\n");
  fprintf (fp, "\nSub absnc(row,col,formula)\n");
  fprintf (fp, "Cells(row,col).Formula=formula\n");
  fprintf (fp, "End sub\n\n");


  fprintf (fp, "Sub absmain()\n");
  fprintf (fp, "'Do not edit this macro, changes will not be saved with the workbook!!!\n");
  fprintf (fp, "Dim objchart  As Object\n");
  fprintf (fp, "Dim objbutton As Object\n");
  for (i = 0; i < workbook->nbworksheet; i++)
    {
      if (i > 2)
	fprintf (fp, "Worksheets.Add\n");
      fprintf (fp, "Worksheets(%d).Name = \"%s\"\n", i + 1, workbook->Worksheets[i]->Name);
    }

  for (i = 0; i < workbook->nbworksheet; i++)
    {
      fprintf (fp, "Worksheets(%d).Activate\n", i + 1);
      if (workbook->Worksheets[i] == workbook->activeworksheet)
	active = i;

      worksheet_write (workbook->Worksheets[i], fp);

    }

  fprintf (fp, "Worksheets(%d).Activate\n", active + 1);	
  fprintf (fp, "End Sub\n");

  fclose (fp);


  

  return 0;
}

extern int rebuild_thumb ();
extern int resetselect (int i, int j, int k);
Workbook *
ActivateWorkbook (workbook)
     Workbook *workbook;
{
  if (workbook == NULL)
    return NULL;
  ActivateProject (workbook->project);
  ActiveWorkbook = workbook;
  
  ActivateWorksheet (ActiveWorkbook->activeworksheet);

  return ActiveWorkbook;
}

Worksheet *
workbook_getsheet (Workbook * workbook, char *name)
{
  int i;
  
  if (name == NULL)
    return NULL;
  for (i = 0; i < workbook->nbworksheet; i++)
    {
      if (strcasecmp (workbook->Worksheets[i]->Name, name) == 0)
	{			
	  return workbook->Worksheets[i];
	}
    }
  fprintf (stderr, "%s worksheet not found!\n", name);
  return workbook->Worksheets[0];

}

Worksheet *
workbook_getsheet2 (workbook, num)
     Workbook *workbook;
     int num;
{

  
  num--;			
  if (num >= 0 && num < workbook->nbworksheet)
    return workbook->Worksheets[num];
  return workbook->Worksheets[0];

}

Worksheet *
workbook_addsheet (Workbook * workbook, char *name)
{
  int i;
  i = workbook->nbworksheet;
  workbook->nbworksheet++;

  workbook->Worksheets =
    (Worksheet **) absrealloc (workbook->Worksheets,
  sizeof (Worksheet *) * (i + 1), "workbook_addsheet:workbook->Worksheets ");

  workbook->Worksheets[i] = newworksheet ();
  if (name == NULL)
    {
      workbook->Worksheets[i]->Name[0] = 'A' + i;
      workbook->Worksheets[i]->Name[1] = '\0';
    }
  else
    strcpy (workbook->Worksheets[i]->Name, name);
  workbook->activeworksheet = workbook->Worksheets[i];
  if (workbook == ActiveWorkbook)
    {
      ActivateWorksheet (ActiveWorkbook->activeworksheet);
    }
  return workbook->Worksheets[i];
}

Worksheet *
workbook_delsheet (workbook, num)
     Workbook *workbook;
     int num;
{
  int i, j;
  num--;			
  i = workbook->nbworksheet;

  if (num < 2 || num > i)
    return NULL;

  freeworksheet (workbook->Worksheets[num]);

  for (j = num; j < workbook->nbworksheet; j++)
    workbook->Worksheets[j] = workbook->Worksheets[j + 1];

  workbook->nbworksheet--;

  (Worksheet **) absrealloc (workbook->Worksheets,
			     sizeof (Worksheet *) * workbook->nbworksheet, "workbook_delsheet:workbook->Worksheets ");

  rebuild_thumb ();
  return workbook->Worksheets[0];
}

Worksheet *
workbook_delactivesheet (workbook)
     Workbook *workbook;
{
  int i, j;
  int num;
  i = workbook->nbworksheet;
  if (i < 2)
    return NULL;

  for (i = 0; i < workbook->nbworksheet; i++)
    if (workbook->Worksheets[i] == workbook->activeworksheet)
      {
	freeworksheet (workbook->activeworksheet);
	for (j = i; j < workbook->nbworksheet; j++)
	  workbook->Worksheets[j] = workbook->Worksheets[j + 1];
	workbook->nbworksheet--;

	if (workbook->nbworksheet > 0)
	  {
	    if (i < workbook->nbworksheet)
	      num = i;
	    else
	      num = workbook->nbworksheet - 1;
	    workbook->activeworksheet = workbook->Worksheets[num];
	    ActivateWorksheet (ActiveWorkbook->activeworksheet);

	    (Worksheet **) absrealloc (workbook->Worksheets,
				       sizeof (Worksheet *) * workbook->nbworksheet, "workbook_delsheet:workbook->Worksheets ");
	  }
	else
	  {
	    workbook->activeworksheet = NULL;
	    rebuild_thumb ();
	  }
      }
  return workbook->activeworksheet;
}


int 
workbook_calculate (Workbook * workbook)
{
  int j;
  for (j = 0; j < workbook->nbworksheet; j++)
    worksheet_calculate (workbook->Worksheets[j]);
  return 0;
}
