/*=============================================================================}
{ Demo:                                                                        }
{ 1. how to load RVF file saved in demo editor.                                }
{ 2. HTML export with custom saving of images                                  }
{------------------------------------------------------------------------------}
{ Providing pictures and controls on request from RichView is not supported in }
{ this demo.                                                                   }
{=============================================================================*/

/*
  This demo uses:
  for Delphi 3-2006: free Anders Melander's TGifImage:
    http://www.torry.net/vcl/graphics/gif/gifimage.exe)
    http://www.trichview.com/resources/thirdparty/gifimage.zip (update)
  for Delphi 2007:
    Standard Delphi TGifImage
*/

#include <vcl\vcl.h>
#pragma hdrstop

#include "Unit1.h"
#include "RVTable.hpp"
#include "WMFCanvasWorkAround.hpp"
//---------------------------------------------------------------------------
#pragma link "RichView"
#pragma link "RVScroll"
#pragma link "RVStyle"
#pragma link "RVTable"
#pragma link "RVTInplace"
#pragma link "GifImage" // <- Change to "GifImg" for C++Builder 2007 or newer
#pragma resource "*.dfm"
TForm1 *Form1;


/*=================== Notes about loading from RVF files:=======================
1. In the simplest cases you can just write: RichView1.LoadRVF(<file name>);
2. If file contains inserted C++Builder Controls, these controls must be registered
   with RegisterClasses functions before loading (see FormCreate below)
3. If file contains images from image lists, you need to process
   OnRVFImageListNeeded event (see RichView1RVFImageListNeeded below)
   If you have several image lists, you can distinguish them using
   ImageListTag parameter of this event.
4. You must have the same (or compatible) TRVStyle object assigned to
   RichView1.Style as in editor.
   Otherwise, you need to set option "Allow adding styles dynamically"
   both in richview which saves and in richview which loads RVF
   (right-click RichView in C++Builder, choose "Settings" in the context menu)
5. If some items in RVF file have character strings associated as items' tags
   (rvoTagsArePChars was in editor's Options), you need also set rvoTagsArePChars
   in RichView1.Options.
==============================================================================*/
/*==================== Notes about HTML export =================================
1. There are 2 methods for saving HTML files:
   a) SaveHTML - saving HTML file, where formatting is made by <FONT>,<B>,
     <I> tags, etc.
   b) SaveHTMLEx - saving HTML file, where formatting is made by Cascading
     Style Sheet (CSS).
2. Images are saved in separate files. By default, they are saved as JPEGs.
3. By default, images are saved in the same directory as HTML file, and have
   names built as Prefix + Number + .JPG.
   You can specify your own prefix as a parameter of SaveHTML[Ex].
   You can include subdirectory in prefix (such as 'images\img'), but this
   subdirectory will NOT be created automatically.
4. JPEGs do not support transparency. Transparent color (of metafiles,
   icons, imagelist images) is replaced with the current background color
   (of RichView or table cell or paragraph background)
5. By default, images from imagelists (bullets and hotspot) are saved like
   other images, but the same image saved only one time (next occurrences
   point to the same image file, if they have the same background color)
6. You can save images yourself using OnHTMLSaveImage event.
   You need to store image to file and return its location in 'Location'
   parameter.
   This demo shows
   a) how to save images in GIF-files
   b) how to save bullets in a way allowing to use the same image files for
      the whole HTML document generated by your application.
7. By default hypertext is not saved.
   You can specify destinations of [some/all] hypertext jumps
   using OnWriteHyperlink event.
8. By default inserted controls are not saved.
   You can save them using OnSaveComponentToFile event
9. You can save additional information in OnSaveHTMLExtra.
==============================================================================*/

//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
    : TForm(Owner)
{
}
//---------------------------------------------------------------------------
void __fastcall TForm1::FormCreate(TObject *Sender)
{
  TComponentClass Classes[3] = { __classid(TButton), __classid(TEdit), __classid(TOleContainer) };
  RegisterClasses(Classes,2);
}
//============================== RVF loading ==================================
void __fastcall TForm1::Button1Click(TObject *Sender)
{
  if (OpenDialog1->Execute())
  {
    if (!RichView1->LoadRVF(OpenDialog1->FileName))
      Application->MessageBox("Error Loading File", NULL, MB_OK);
    RichView1->Format();
  }
}
//---------------------------------------------------------------------------
void __fastcall TForm1::RichView1RVFImageListNeeded(TCustomRichView *Sender,
    int ImageListTag, TCustomImageList *&il)
{
  il = ImageList1;
}
//============================ Hypertext testing ==============================
void __fastcall TForm1::RichView1RVMouseMove(TObject *Sender, int id)
{
  if (id==-1)
    StatusBar1->SimpleText = "";
  else
  {
    TCustomRVFormattedData* RVData;
    int ItemNo;
    RichView1->GetJumpPointLocation(id, RVData, ItemNo);
    StatusBar1->SimpleText = (char*)RVData->GetItemTag(ItemNo);
  }
}
//---------------------------------------------------------------------------
void __fastcall TForm1::RichView1Jump(TObject *Sender, int id)
{
  TCustomRVFormattedData* RVData;
  int ItemNo;
  RichView1->GetJumpPointLocation(id, RVData, ItemNo);
  StatusBar1->SimpleText = (char*)RVData->GetItemTag(ItemNo);
  Application->MessageBox(StatusBar1->SimpleText.c_str(),"Click", 0);
}
//=========================== SAVING TO HTML ==================================
void __fastcall TForm1::Button2Click(TObject *Sender)
{
  TRVSaveOptions SaveOptions = TRVSaveOptions();
  bool r;
  if (SaveDialog1->Execute())
  {
    Screen->Cursor = crHourGlass;
    if (CheckBox1->Checked)
      SaveOptions << rvsoOverrideImages;
    else
      SaveOptions >> rvsoOverrideImages;
    switch (SaveDialog1->FilterIndex)
    {
      case 1:
        r = RichView1->SaveHTML(SaveDialog1->FileName,"Demo File",Edit2->Text, SaveOptions);
        break;
      case 2:
        r = RichView1->SaveHTMLEx(SaveDialog1->FileName,"Demo File",Edit1->Text,
                                      "","","",SaveOptions);
        break;
      default:
        r = false;
    }
    Screen->Cursor = crDefault;
    if (!r)
      Application->MessageBox("Error during saving", "Error", MB_OK);
  }
}
//---------------------------------------------------------------------------
// Event: overriding default saving of images - saving as Gifs
void __fastcall TForm1::RichView1HTMLSaveImage(TCustomRichView *Sender,
    TCustomRVData *RVData, int ItemNo, const AnsiString Path,
    TColor BackgroundColor, AnsiString &Location, bool &DoDefault)
{
  TRVVAlign AVAlign;
  int ATag;
  TCustomImageList* ImageList;
  int ImageIndex;
  AnsiString s;
  TGraphic* gr;

  // Parameters:
  //The item to save is defined by the pair (RVData, ItemNo).
  // It is the ItemNo-th item in RVData object.
  // RVData may be RichView.RVData, or cell, or RVData of cell inplace editor.
  // Path - destination directory of HTML file.
  // BackgroundColor - color of background under this item. Not used here
  // because GIFs support a true transparency.
  // Location - output parameter to specify filename of image file
  // DoDefault - set to false if you save this item as image yourself.

  if (ItemNo<0)
  {
    // saving background
     TGIFImage* gif = new TGIFImage;
     try
     {
       gif->ColorReduction = rmQuantize;
       if (RVData->InheritsFrom(__classid(TRVTableCellData)))
         gif->Assign(((TRVTableCellData*)RVData)->BackgroundImage);
       else
         gif->Assign(Sender->BackgroundBitmap);
       Location = RVData->GetNextFileName(Edit2->Text, Path, ".gif",
         RichView1->imgSaveNo, CheckBox1->Checked);
       gif->SaveToFile(Location);
       Location = ExtractRelativePath(Path, Location);
       DoDefault = false;
     }
     catch(...)
     {
     }
     delete gif;
     return;
  }
  TGIFImage* gif = NULL;
  switch (RVData->GetItemStyle(ItemNo))
  {
    case rvsPicture:
    case rvsHotPicture:
    {
      // Assigning image to GIF and saving
      // (metafiles and icons will be saved with transparency)
      gif = new TGIFImage;
      gif->ColorReduction = rmQuantize;
      RVData->GetPictureInfo(ItemNo, s, gr, AVAlign, ATag);
      gif->Assign(gr);
      Location = RVData->GetNextFileName(Edit2->Text, Path, ".gif", RichView1->imgSaveNo, CheckBox1->Checked);
      break;
    }
    case rvsTable:
    {
      gif = new TGIFImage;
      gif->ColorReduction = rmQuantize;
      TRVTableItemInfo * table = (TRVTableItemInfo*)(RVData->GetItem(ItemNo));
      gif->Assign(table->BackgroundImage);
      Location = RVData->GetNextFileName(Edit2->Text, Path, ".gif", RichView1->imgSaveNo, CheckBox1->Checked);
      break;
    }
    case rvsBullet:
    case rvsHotspot:
    {
      // This is not an efficient way, because the same image will be
      // saved many times. In your application you can save bullets
      // before saving HTMLs, and here only return file name.
      RVData->GetBulletInfo(ItemNo, s, ImageIndex, ImageList, ATag);
      TMetafile* wmf = new TMetafile;
      try
      {
        gif = new TGIFImage;
        gif->ColorReduction = rmQuantize;
        // Drawing image from imagelist to metafile
        // This method allows to save transparency
        wmf->Width  = ((TImageList*)ImageList)->Width;
        wmf->Height = ((TImageList*)ImageList)->Height;
        TCanvas * Canvas = CreateMetafileCanvas(wmf); // workaround for C++Builder 5 problem
        ImageList->Draw(Canvas,0,0, ImageIndex
#if __BORLANDC__>0x0530
        , true // if not C++Builder 3
#endif
        );
        delete Canvas;
        // Assigning metafile to GIF and saving
        gif->Assign(wmf);
        // Saving to Path + Bullets Prefix + ImageIndex + .gif
        Location = Format("%s%s%d.gif", ARRAYOFCONST((Path, Edit1->Text, ImageIndex)));
      }
      catch(...)
      {
      }
      delete wmf;
      break;
    }
  }
  if (gif)
  {
    gif->SaveToFile(Location);
    Location = ExtractRelativePath(Path, Location);
    DoDefault = false;
    delete gif;
  }
}
//---------------------------------------------------------------------------
// Event: saving hyperlinks
void __fastcall TForm1::RichView1WriteHyperlink(TCustomRichView *Sender,
      int id, TCustomRVData *RVData, int ItemNo, TRVSaveFormat SaveFormat,
      AnsiString &Target, AnsiString &Extras)
{
  Target = (char*)(RVData->GetItemTag(ItemNo));
}
//---------------------------------------------------------------------------
// Event: saving components
void __fastcall TForm1::RichView1SaveComponentToFile(
      TCustomRichView *Sender, AnsiString Path, TPersistent *SaveMe,
      TRVSaveFormat SaveFormat, AnsiString &OutStr)
{
  switch (SaveFormat)
  {
    case rvsfHTML:
    {
      if (SaveMe->InheritsFrom(__classid(TButton)))
      {
        OutStr = "<INPUT type=\"button\" value=\""+((TButton*)SaveMe)->Caption+"\" "+
          "onClick=\"alert('Just a demo')\">";
        return;
      }
      if (SaveMe->InheritsFrom(__classid(TEdit)))
      {
        OutStr = "<INPUT type=\"text\" value=\""+((TEdit*)SaveMe)->Text+"\">";
        return;
      }
      break;
    }
  }
}
//---------------------------------------------------------------------------
// Event: saving additional information
void __fastcall TForm1::RichView1SaveHTMLExtra(TCustomRichView *Sender,
      TRVHTMLSaveArea Area, bool CSSVersion, AnsiString &HTMLCode)
{
  switch (Area)
  {
    case rv_thms_Head:
      HTMLCode = "<script></script>";
      break;
    case rv_thms_BodyAttribute:
      HTMLCode = "alink=#ff0000";
      break;
    case rv_thms_Body:
      HTMLCode = "This document was generated by "
        "<A href=\"http://www.trichview.com\">RichView</A><BR>";
      break;
  }
}
//---------------------------------------------------------------------------

