use strict;
use vars qw($pDataSetMGL @pDataSetMGL %hFormDataMGL $oDbSessionGL);

use PDF::Create;

use constant ROTATE      => 90;

{
my $iActualYPosGL   = 0;
my $iActualXPosGL   = 0;
my $iPageGL         = 0;
my $iRecordSizeGL   = 0;
                    
my $iPageWidthGL    = 0;
my $iPageHeightGL   = 0;
my $iFieldSizeGL    = 0;
                    
my $iLeftBorderGL   = 0;
my $iRightBorderGL  = 0;
my $iTopBorderGL    = 0;
my $iBotBorderGL    = 0;
my $iHeaderSizeGL   = 0;
my $iFooterSizeGL   = 0;
my $iColGL          = 0;

sub BtnReport()
{
   my %hDataDesc = ();
   my $cField;
   my $cKey;
   my $cName;
   my $cOp;
   my $cRecIdFields;
   my $cResult;
   my $cValue;
   my $iInd;
   my $pRecord;
   my @lFields = (split /, */,
				  &MyVal('Data', 'PdfFields', 
						 &MyVal('Data', 'QryFields')));

   $iRecordSizeGL = &MyVal('PDF', 'RecordSize',   45);
   $iFieldSizeGL  = &MyVal('PDF', 'FieldSize',   100);
   
   $iPageWidthGL  = &MyVal('PDF', 'PageWidth',   612);
   $iPageHeightGL = &MyVal('PDF', 'PageHeight',  792);
   
   $iLeftBorderGL  = &MyVal('PDF', 'LeftBorder',  10);
   $iRightBorderGL = &MyVal('PDF', 'RightBorder', 10);
   $iTopBorderGL   = &MyVal('PDF', 'TopBorder',    5);
   $iBotBorderGL   = &MyVal('PDF', 'BotBorder',    5);
   $iHeaderSizeGL  = &MyVal('PDF', 'HeaderSize',  60);
   $iFooterSizeGL  = &MyVal('PDF', 'FooterSize',  30);

   $cRecIdFields      = &GetAttr("RecIdField");

   # add id-field to the query
   &MyParam("!Fields",
            ((&MyVal('Qry', 'Distinct')? "DISTINCT ":  "") .
             &MyVal('Data', 'PdfFields', &MyVal('Data', 'QryFields')) .
             ", " . $cRecIdFields ));

   &InitDBIxRecordset();

   # Here the User can manipulate form-data
   Plugin->new("PreCreateForm")->Call();

   # create recordset
   *pDataSetMGL = DBIx::Recordset->Setup(\%hFormDataMGL);

   # Get the type-info for the fields
   &GetAllFieldInfo(&MyVal('Data', 'Table'), $pDataSetMGL);

   # construct selection-criteria
   foreach $cKey (keys %hFormDataMGL)
   {

      if ($cKey =~ "^Fld.*" and &MyParam($cKey) ne "")
      {

         # get the fieldname
         ($cField = $cKey) =~ s/^Fld//;

         # we got an operator
         if(&MyParam("\*$cField"))
         {
            &MyParam($cKey,
                     &MyParam("\*$cField") . " " .
                     &MyParam("$cField"));

         }

         # now scan the search-operator
         if(&MyParam($cKey) =~ /^(>=|<=|<|>|!=|=|like)\s*(.*)$/)
         {
            ($cOp, $cValue) = ($1, $2);
         }
         else # no search-operator
         {
            # * is replaced with LIKE
            if (&MyParam($cKey) =~ /\*/)
            {
               ($cValue = &MyParam($cKey)) =~ s/\*/%/g;
               $cOp     = "like";

            }
            else
            {
               $cOp    = "=";
               $cValue = &MyParam($cKey);
            }
         }

         # make this field ready for querying the database
         &MyParam($cKey, $cValue);

         &ConvertDataForDb("Form2Db", $cField);
         $cValue = &MyParam($cKey);

         if($cValue)
         {
             &MyParam("\*$cField", $cOp);
             &MyParam("$cField", $cValue);

             printf STDERR sprintf(i18n("%s => Op: s(%s) Value: s(%s)") .
                                      "<BR>\n",
                                      $cField,
                                      $cOp,
                                      $cValue)
                 if &GetAttr("DebugLvl") > 3;
         }
      } # if ($cKey =~ "Fld.*" and &MyParam($cKey) ne "")
   } # foreach $cKey (keys %hFormDataMGL)

   &InitDBIxRecordset();

   &MyParam('$max', 100000);
   &MyParam('$valuesplit', ",");
   &MyParam('$compconj',   "and");

   &MyParam('$start', "0");

   # Search for Data
   $pDataSetMGL->Search(\%hFormDataMGL);

   # catch DB-error
   &DbiErrorAndExit(i18n("data-querying"));

   print CGI::header(-type       => 'application/pdf',
                     -attachment => &MyVal('Data', 'Table') . ".pdf",
                     -expires    => '+3d');

   my $oPDF = new PDF::Create('fh'       => *STDOUT,
                              'Author'   => 'WWWdb',
                              'PageMode' => 'UseOutlines',
                              'Title'    => &MyVal('PDF', 'Title',
												   &MyVal('Header', 'Title')),
                              'Rotate'    => ROTATE
                              );

   my $oRoot = $oPDF->new_page('MediaBox'  => [ 0, 0, $iPageWidthGL, $iPageHeightGL ]);

   # Add a page which inherits its attributes from $oRoot
   my $oPage = $oRoot->new_page;

   # Prepare 2 fonts
   my $oTextFont = $oPDF->font('Subtype'  => 'Type1',
                               'Encoding' => 'WinAnsiEncoding',
                               'BaseFont' => 'Helvetica');

   &GenHeader($oPDF, $oPage);
   $iInd = 0;

   $iColGL = 0;
   # Initialize Data-Descriptions
   foreach $cName (@lFields)
   {
	   
	   my $cValue;
	   
	   ($hDataDesc{$cName}{'YPos'}, 
		$hDataDesc{$cName}{'XPos'}) = 
			split(",", &MyVal("Layout PDF $cName", 'Pos',
							  sprintf("%d,%d",
									  ($iColGL * $iFieldSizeGL),
									  0)));
	   $hDataDesc{$cName}{'FontSize'} = &MyVal("Layout PDF $cName", 'FontSize', 
											   &MyVal("PDF", 'FontSize', 10));
	   $hDataDesc{$cName}{'Align'}    = &MyVal("Layout PDF $cName", 'Align', 'Left');
	   
	   # Try to plug in PdfConv_${cName}
       $hDataDesc{$cName}{'Plugin'}   = Plugin->new("PdfConv_${cName}");

	   # Try to plug in QryConv_${cName} if the previous one failed
	   $hDataDesc{$cName}{'Plugin'}   = Plugin->new("QryConv_${cName}")
		   unless $hDataDesc{$cName}{'Plugin'}->IsDefined("Default");

	   # undef all ...
	   $hDataDesc{$cName}{'Plugin'}   = undef
		   unless $hDataDesc{$cName}{'Plugin'}->IsDefined("Default");
	   

			   
	   $iColGL ++;

   }


   $iInd = 0;
   while ($pRecord = $pDataSetMGL[$iInd])
   {
      my $iLine;
      my $iMaxYOffset = 0;
	  

      $iActualYPosGL += $iRecordSizeGL;

      # generate the data-fields
      foreach $cName (@lFields)
      {

         my $cValue;
         my $iYPos     = $hDataDesc{$cName}{'YPos'};
		 my $iXPos     = $hDataDesc{$cName}{'XPos'};
		 my $iFontSize = $hDataDesc{$cName}{'FontSize'};
		 my $cAlign    = $hDataDesc{$cName}{'Align'};

         $iMaxYOffset = $iYPos
             if ($iMaxYOffset < $iYPos);

         $cValue = $$pRecord{$cName};

         # unmask all " to '
         $cValue =~ s/\"/\'/g;

         # unmask all \r to ' '
         $cValue =~ s/\r//g;
         $cValue =~ s/\n/ /g;

         # compress spaces
         $cValue =~ s/\s+/ /g;

		 # Call plugin for formatting
		 $cValue = $hDataDesc{$cName}{'Plugin'}->Call($cValue, %{$pRecord})
			 if defined $hDataDesc{$cName}{'Plugin'};

         &GenText($oPage,
                  $oTextFont,
                  $iFontSize,
                  $iXPos,
                  $iActualYPosGL + $iYPos,
				  $cAlign,
                  $cValue);



      }

      $iActualYPosGL += 3;

      if(($iActualYPosGL + $iFooterSizeGL + $iRecordSizeGL * 2) >= $iPageHeightGL)
      {
         # Add a page which inherits its attributes from $oRoot
         $oPage = $oRoot->new_page;
         &GenHeader($oPDF, $oPage);

      }
	  else
	  {

		  # draw a line at the end of each record
		  $oPage->line($iLeftBorderGL,                                     # to x
					   &PDF_LineCoord($iActualYPosGL + $iRecordSizeGL - 10), # to y
					   $iPageWidthGL - $iRightBorderGL,                    # from x
					   &PDF_LineCoord($iActualYPosGL + $iRecordSizeGL - 10)   # from y
					   );
	  }

      $iInd ++;

   } # while ($pRecord = $pDataSetMGL[$iInd++])
   # quit here explicitly

   # Add the missing PDF objects and a the footer then close the file
   $oPDF->close;

   close STDOUT;                # FIXME: Dangerous
   exit;

} # sub QryData

sub GenText($$$$$$$;$)
{
   my $pPagePI     = shift;
   my $pFontPI     = shift;
   my $iFontSizePI = shift;
   my $iXPosPI     = shift;
   my $iYPosPI     = shift;
   my $cAlignPI    = shift;
   my $cTextPI     = shift;
   
   # optional
   my $iSizePI     = shift;

   if (lc($cAlignPI) eq "center")
   {
	   $pPagePI->stringc($pFontPI,
						 $iFontSizePI,
						 $iLeftBorderGL + $iXPosPI,
						 &PDF_LineCoord($iYPosPI),
						 $cTextPI);
   }
   elsif (lc($cAlignPI) eq "right")
   {
	   $pPagePI->stringr($pFontPI,
						 $iFontSizePI,
						 $iLeftBorderGL + $iXPosPI,
						 &PDF_LineCoord($iYPosPI),
						 $cTextPI);
   }
   else
   {
	   $pPagePI->string($pFontPI,
						$iFontSizePI,
						$iLeftBorderGL + $iXPosPI,
						&PDF_LineCoord($iYPosPI),
						$cTextPI);
   }

   return $cTextPI;
}

sub PDF_LineCoord($)
{
   my $iPos_PI = shift;

   return ($iPageHeightGL - $iPos_PI);

}

sub GenHeader()
{
   my $pPdf_PI  = shift;
   my $pPage_PI = shift;
   
   my $oHeaderFont = $pPdf_PI->font('Subtype'  => 'Type1',
									'Encoding' => 'WinAnsiEncoding',
									'BaseFont' => 'Helvetica-Bold');

   $iPageGL ++;

   # Header
   {
      my $cName;
      my $iColGL = 0;

      $pPage_PI->stringc($oHeaderFont, 16,
                         $iLeftBorderGL + ($iPageWidthGL / 2) - $iRightBorderGL, # column
                         &PDF_LineCoord($iTopBorderGL + ($iHeaderSizeGL / 4)), # line
                         &MyVal('PDF', 'Title', &MyVal('Header', 'Title')));

      foreach $cName (split /, */,
                      &MyVal('Data', 'QryFields'))
      {
		 my $cAlign      = &MyVal("Layout PDF $cName", 'Align', $cName);
         my $cFieldLabel = &MyVal("Layout PDF $cName", 'Label', $cName);
         my ($iYPos, $iXPos) = split(",",
                                     &MyVal("Layout PDF $cName", 'Pos',
                                            sprintf("%d,%d",
                                                    ($iColGL * $iFieldSizeGL),
                                                    0)));

		 

         &GenText($pPage_PI,
                  $oHeaderFont,
                  11,
                  $iXPos,
                  $iTopBorderGL + $iHeaderSizeGL / 2 + $iYPos,
				  $cAlign,
                  i18n($cFieldLabel));

         $iColGL ++;
      }

      # header-line
      $pPage_PI->line($iLeftBorderGL, # from x
                      &PDF_LineCoord($iTopBorderGL + ($iHeaderSizeGL - 2)),    # from y
                      $iPageWidthGL - $iRightBorderGL, # to x
                      &PDF_LineCoord($iTopBorderGL + ($iHeaderSizeGL - 2))     # to y
                      );
   }

   # Footer
   {
      # footer-line
      $pPage_PI->line($iLeftBorderGL, # from x
                      &PDF_LineCoord($iPageHeightGL - $iFooterSizeGL + 2), # from y
                      $iPageWidthGL - $iRightBorderGL, # to x
                      &PDF_LineCoord($iPageHeightGL - $iFooterSizeGL + 2)  # to y
                      );

      # left text
      $pPage_PI->stringl($oHeaderFont, 10, 
                         $iLeftBorderGL, # column
                         &PDF_LineCoord($iPageHeightGL - ($iFooterSizeGL / 2)), # line
                         i18n("Date: ") .
                         ($oDbSessionGL->DateFromDb(scalar(localtime()))));

      # centered text
      $pPage_PI->stringc($oHeaderFont, 10,
                         $iLeftBorderGL + (($iPageWidthGL - $iLeftBorderGL) / 2) - $iRightBorderGL, # column
                         &PDF_LineCoord($iPageHeightGL - ($iFooterSizeGL / 2)), # line
                         "");

      # right text
      $pPage_PI->stringr($oHeaderFont, 10,
                         $iPageWidthGL - $iRightBorderGL, # column
                         &PDF_LineCoord($iPageHeightGL - ($iFooterSizeGL / 2)), # line
                         i18n("Page ") . $iPageGL);
   }

   $iActualYPosGL = $iHeaderSizeGL + $iTopBorderGL;
}
}

1;
