#include <relapp.h>  
#include <msksheet.h>
#include <stdtypes.h>
#include <lffiles.h>
#include "ba4.h"
#include "ba4100.h"
#define FIRST_YEAR 1993

class BA4100_application : public TRelation_application
{
  TMask * _msk;
  TRelation * _rel;
  TLocalisamfile * _alici;
  TRecord_array * _alici_rec;
  static bool fld_notify(TSheet_field& s, int r, KEY k);
  virtual bool user_create() ;                         
  virtual bool user_destroy() ;                        
  virtual bool changing_mask(int mode) { return FALSE;}
  virtual TRelation* get_relation() const { return _rel;}
  virtual int read(TMask& m);                    
  virtual int write(const TMask& m);             
  virtual int rewrite(const TMask& m);           
  virtual bool remove();                        

public:
  virtual TMask* get_mask(int mode) { return _msk;}
  BA4100_application() {}
  virtual ~BA4100_application() {}           
  TRecord_array & alici_rec() { return * _alici_rec; }
};

BA4100_application & app() { return (BA4100_application &) main_app(); }

bool BA4100_application::fld_notify(TSheet_field& f, int r, KEY k)
{
  if (k == K_INS)
  {
    TMask& m = f.sheet_mask();
    TToken_string & t = f.row(r);

    t.format("%d", r + FIRST_YEAR);
    t.add("");
    t.add("");
  }
  return TRUE;
}
bool BA4100_application::user_create()
{
  _msk = new TMask("ba4100a") ;
  TSheet_field& f = (TSheet_field&) _msk->field(FLD_CM2_ALIQICI);
  f.set_notify(fld_notify);
  _rel = new TRelation(LF_COMUNI);
  _alici = new TLocalisamfile(LF_ALICI);
  _alici_rec =  new TRecord_array(LF_ALICI, "ANNO", FIRST_YEAR);
  return TRUE;
}

bool BA4100_application::user_destroy()
{
  delete  _msk;
  delete  _rel;                         
  delete        _alici;              
  delete _alici_rec;
  return TRUE;
}

int BA4100_application::read(TMask& m)
{ 
  int err = TRelation_application::read(m);
  if (err == NOERR)                                             
  {                       
    TRectype r = _alici->curr();
    
    r.zero();
    r.put("COM", m.get(FLD_CM1_COM)); 
    _alici_rec->read(r);                   // Ignora errori di lettura aliquote ICI
    
    TSheet_field& f = (TSheet_field&) m.field(FLD_CM2_ALIQICI);
    f.destroy();
    int last = _alici_rec->last_row();
    const int year = TDate(TODAY).year();
    
    if (last < year) last = year;
    for (int i = FIRST_YEAR; i <= last; i++)
    {
      TRectype & r = _alici_rec->row(i, TRUE); 
      TToken_string & t = f.row(i - FIRST_YEAR);
      
      t = r.get("ANNO");
      t.add(r.get("ALIQ"));
      t.add(r.get("DETR"));                                          
    }
  }
  return err;
}

int BA4100_application::write(const TMask& m)
{
  int err = TRelation_application::write(m);
  if (err == NOERR) 
  {   
    TSheet_field& f = (TSheet_field&) m.field(FLD_CM2_ALIQICI);
    _alici_rec->destroy_rows();
    if (m.insert_mode())   
      _alici_rec->renum_key("COM", m.get(FLD_CM1_COM));
    
    for (int i = 0; i < f.items(); i++)
    {
      TToken_string & t = f.row(i);
      const real aliq(t.get(1));
      const real detr(t.get());
      if (aliq != ZERO || detr != ZERO)
      {
        TRectype & r = _alici_rec->row(t.get_int(0), TRUE); 
        
        r.put("ALIQ", aliq);
        r.put("DETR", detr);
      }                                          
    }    
    err = _alici_rec->write();
  }
  return err;
}

int BA4100_application::rewrite(const TMask& m)
{ 
  int err = TRelation_application::rewrite(m);
  if (err == NOERR) 
  {
    TSheet_field& f = (TSheet_field&) m.field(FLD_CM2_ALIQICI);
    _alici_rec->destroy_rows();
    if (m.insert_mode())   
      _alici_rec->renum_key("COM", m.get(FLD_CM1_COM));
    
    for (int i = 0; i < f.items(); i++)
    {
      TToken_string & t = f.row(i);
      const real aliq(t.get(1));
      const real detr(t.get());
      if (aliq != ZERO || detr != ZERO)
      {
        TRectype & r = _alici_rec->row(t.get_int(0), TRUE); 
        
        r.put("ALIQ", aliq);
        r.put("DETR", detr);
      }                                          
    }
    err = _alici_rec->rewrite();
  }  
  return err;
}

bool BA4100_application::remove()

{
  return TRelation_application::remove() && _alici_rec->remove() == NOERR; 
}

int ba4100(int argc, char* argv[])
{
  BA4100_application a ;
  a.run(argc, argv, "Anagrafica Comuni");
  return 0;
}
