RReport (com.java4less.rreport)

Introduction

Wellcome to RReport, the package that will allow you to include printing, reporting and prevewing capablities into yourJava [TM] or Web applications (JDK 1.1 or newer) in a few minutes. RReport is located in the package com.java4less.rreport

The main features or RReport are:

 

Creating a report

Before you start reading this section you must note that there are 2 ways for creating reports:

  1. you can programatically create all the objects that make a report and link them together.
  2. or you can use RReport Visual Builder in order to visually create a report. This will be exported to a definition file *.rep that you can import in your application. We recommend this approach.

You can, of course, also combine both approaches. For example, you can create a report template (*.rep file) and modify it at runtime.

There are 4classes that represent a report

  1. RReport: basic class. It uses Java 1.1 printing API. This version is Java 1.1 compatible.
  2. RReportImp: this is a subclass of RReport that will allow you to read a definition file (*.rep) created with RReport Visual Builder. For this purpose it includes a importReport() method.
  3. RReportJ2: this is a subclass of RReportImp that uses Java 2 printing API (printerJob). This version has the following advantages:
  4. RReportJ2X: Subclass of RReport that uses features only available in the Java platform 1.4 or later. For example, it allows you to select a given printer by program.

 

A Rreport is made of Rareas. A RArea is a group of objects (RObject) that will be printed together (in the same page). Typical examples of areas in a report are:

 

The source code to create an area looks like this:

// create report
Rreport Rep=new RReport(MainWindow);
// if you use java 1.2 or later you can use
// Rep=new RReportJ2(null);


RArea HDR_PurchaseOrder= new RArea();
HDR_PurchaseOrder.width=16.429;
HDR_PurchaseOrder.height=4.074;
Rep.addArea(HDR_PurchaseOrder);

As already stated, an RArea contains of a set of objects (RObject). These are the elements that are actually printed. The following Robjects are currently available:

The following example creates the page footer for the Purchase order report:

RArea PFOOTER_PurchaseOrder= new RArea();
RField TextPageNumber=new RField();
TextPageNumber.name="TextPageNUmber";
TextPageNumber.setConstant(false);
TextPageNumber.setdefaultValue("[Page]");
TextPageNumber.x=0.238;
TextPageNumber.y=0.185;
TextPageNumber.width=3;
TextPageNumber.height=0.423;
TextPageNumber.Align=RField.ALIGN_LEFT;
TextPageNumber.Expand=false;
TextPageNumber.Compress=false;
TextPageNumber.FontColor=java.awt.Color.black;
TextPageNumber.FontType=new java.awt.Font("Arial",java.awt.Font.PLAIN,8);
PFOOTER_PurchaseOrder.add(TextPageNumber);

rep.setPageFooter(PFOOTER_PurchaseOrder);

The code:

Actually this would not be necessary. When you create a new RReport it already contains a default pager footer like this one.

Note: if you are using RReport Visual Builder you will not do this, you will read the definition of your report from a file.

If you want to modify a RField in a report created with the Visual Builder you can do it like this:

RField f=(RField) report.getAreaByName(name).getItemByName(elementName);

 

Nested (linked) Areas

Areas can be nested by linking them to a superarea (see RArea.setLinkedArea() ). After a repetition of an area is printed, all subareas are printed automatically.

For example:

detailArea.setLinkedArea(headerArea);

will result in detailArea being printed after each repetition of headerArea. See RJDBCSource to learn how to retrieve the information from a database and define relationships between tables.

Let's suppose your report has 2 areas (header and detail). You have 2 options:

 

 

Groups of Areas

You can create a group of areas using RReport Visual Builder. A group of areas is made of:

The groups of areas will allow you to automatically print a header and/or a footer based on the values of one or more fields.

The groups of areas must be used together with a RSource (normally a RJDBCSource) and you should set a value for the "GroupByFields" property of the detail area, there is no other special treatment, you can print the group's detail area as you would print any other area.

RReport will automatically print the group header and footer areas whenever the values of the "group by" fields change. Note that the header and footer area share the same RSource as the detail area.

For example , if you are printing the following data in you group detail:

Article Id =1 , Name=Printer , Category=Hardware
Article Id =2 , Name=Scanner , Category=Hardware
Article Id =3 , Name=Antivirus , Category=Software
Article Id =4 , Name=Editor , Category=Software
Article Id =5 , Name=Linux , Category=Software

and you set Group by "Category". The result will be:

  1. Group header is printed
  2. article 1 is printed
  3. article 2 is printed
  4. Group footer is printed
  5. Group header is printed
  6. article 3 is printed
  7. article 4 is printed
  8. article 5 is printed
  9. Group footer is printed

Note that RReport will NOT SORT the values. You must provide the data for the detail area in the correct order. In the previous example you would use a sql statement like: "select * from Articles order by Category" to make sure all articles in the same category come together.

You can find an example of use of groups in the examples/groups folder.

Printing a report

After you have defined your report (either programatically or with the Visual Builder) , you will need to print it. First you must decide if you want to print it directy or you want to preview it.

If you want to preview the report you need to put the RReport object on a component. The RReport object is a java.awt.Panel so you can put it on any java container. Then you must call the report‘s method setPreview(MainWindow).

You can create your own preview window however we include two preview windows. One of them is a pure AWT component (RReportWindow) and the second is a Swing component (RReportJWindow). The code to use the window is:

Win= new RReportWindow(rep,MainWindow);
// if you use SWING:
// Win= new RReportJWindow(rep,MainWindow);

report.prepare();


// Print here ....


report.endReport();
Win.show();

In order to print a report you must follow these steps:

  1. Call prepare(). This will print your report header.
  2. Print the areas. You can either print the areas by assigning the values to the elements yourself (programatically) or you can provide a data source (RSource).
  3. Call endReport(). This will print your report footer.

Note: report header anf footer and page header and footers are printed automatically. If you need to execute your own code before these areas a printed you must use a RAreaListener.

Tip: if you make all your areas dependent of the report header using the setLinkedArea(), then all areas will be printed automatically when you call prepare(). (i.e. the header will be printed and all its subareas).

Note: the prepare() method will print one repetition of the report header. If you assign a RSource (array, table in database ...) to the report header, several repetitions of the header and all subareas will be printed. For each new report header repetition a page break and a initialisation of the page number is automatically performed. In this way you can print more than 1 report at once.

 

The preview Window

RReport comes with two implementations of a preview window (RReportWindow and RReportJWindow ). However if you don‘t like them you can create your own preview window. RReport is an extension from Panel so you can add it to any of your windows, panels etc..

The following methods in RReport will help you building your own user interface:

Data sources (Rsource)

Areas are programatically printed by:

  1. Assigning a value to the elements in the area. The following command assigns the value "Article1" to the element "TextDescription".

    DETAIL_PurchaseOrder.getItemByName("TextDescription").setruntimeValue("Article1");

    and Calling the report’s printArea() method: rep.printArea(DETAIL_PurchaseOrder);

  2. or if they are linked to a superarea, after the superarea is printed.

However you can also use a Rsource object. In this case the report will automatically assing the values to the fields and print the area as many times as needed. There are 4 implemented Rsource classes, but you can implement your own class.

The following example uses the class RArraySource to print the lines of a Purchase Order:

private static void Example2() {


// example: array as data source
Win= new RReportWindow(rep,MainWindow);
DETAIL_PurchaseOrder.setDataSource(new RArraySource(columnsNames,columnsData));
rep.prepare();

//print here
rep.printArea(DETAIL_PurchaseOrder);

rep.endReport();
Win.show();

}

The array columnsNames contains the names of the fields and the array columnsData contanins the values. See Examples or exampleOrder.java.

Note: you can use a RAreaListener in order to execute your own java code before each repetition of the area is printed.

Note: objects defined as constant (see RObject.setConstant()) will not be modified by the data source (RSource).

 

Reading from Xml files

Note: this feature requires you to copy vesion 2.6.0 of xalan.jar, xml-apis.jar and xecesImpl.jar to the RReport's directory. These files are part of the Apache Xalan package.

You can use one or more xml files as data source for your report. The RXMLSource class can be used for this purpose.

Each area can have its own xml file as data source or they can share files with other areas. Each area must also be related to a set of nodes in the xml file (the set of nodes is defined using a xpath expression). RReport will create a new repetition of the area for each node referenced by the XPath.

The constructor must be used to specify the file and the node associated to an area.

RXMLSource(String sFile,String node)

If the sFile parameter is null or empty, the file of the superarea will be used (only if the area has a superarea). In this case the node xpath will be relative to the current node in the superarea.

You must use the RObject.xpath property to specify the data source for the fields in the area. This xpath is relative to the xpath of the area.

The following report template shows how to configure a XML data source using RReport Visual Builder examples/XMLSource/xmlorder.rep. The file examples/XMLSource/documents.xml is used as data source for the report.

You can also create the data source using java code in the following way:

// create data sources
report.getReportHeader().setDataSource(new RXMLSource("documents.xml","/documents/purchaseorder"));
report.getAreaByName("Detail").setDataSource(new RXMLSource("","line")); // line is relative to
/documents/purchaseorder

// link areas and data sources , detail to header
report.getAreaByName("Detail").setLinkedArea(report.getReportHeader());
report.getAreaByName("Detail").getDataSource().setLinkSource(report.getReportHeader().getDataSource());

// set xpaths for header fields, xpaths relative to /documents/purchaseorder
report.getReportHeader().getItemByName("Number").xPath="Number/text()";
report.getReportHeader().getItemByName("Date").xPath="Date/text()";
report.getReportHeader().getItemByName("Company").xPath="Company/text()";
report.getReportHeader().getItemByName("City").xPath="City/text()";
report.getReportHeader().getItemByName("address").xPath="address/text()";

// set xpaths for detail fields, xpaths relative to line
report.getAreaByName("Detail").getItemByName("Article").xPath="article/text()";
report.getAreaByName("Detail").getItemByName("Description").xPath="Description/text()";
report.getAreaByName("Detail").getItemByName("Price").xPath="Price/text()";
report.getAreaByName("Detail").getItemByName("Quantity").xPath="Quantity/text()";
report.getAreaByName("Detail").getItemByName("Priority").xPath="Priority/text()";

 

Reading from database (RJDBCSource)

The class RJDBCSource is a subclass of RSouce. It will therefore allow you to print the contents of a table in a database. Furthermore RJDBCSource supports nested areas. This means you can print an area that contains subareas.

Let's suppose you must print 2 Invoices. Invoice number 1 and invoice number 2. You have a database that contains two tables: INVOICES and INVOICESLINES.

You have defined the following areas for this:

in order to programatically print the two invoices you must:

  1. Retrieve the header's data for invoice 1 (you should query the database like "SELECT * FROM INVOICES WHERE KEY=1")
  2. print header 1
  3. Retrieve the lines for invoice 1 (you should query the database like "SELECT * FROM INVOICESLINES WHERE KEY=1")
  4. print all lines for invoice 1
  5. Retrieve the header's data for invoice 1 (you should query the database like "SELECT * FROM INVOICES WHERE KEY=2")
  6. print header 2
  7. Retrieve the lines for invoice 2 (you should query the database like "SELECT * FROM INVOICESLINES WHERE KEY=2")
  8. print all lines for invoice 2

You can easily simplify this process by using RJDBCSource in the following way.

 

// create source table
RJBCSource headerTable=new RJBCSource(statement,"SELECT * FROM INVOICES");
headerArea.setDataSource(headerTable);

// create source table
RJBCSource linesTable =new RJBCSource(statement,"SELECT * FROM INVOICESLINES");
linesArea.setDataSource(linesTable);

// link areas
linesArea.setLinkArea(headerArea);

// link fields
linesTable.setToFields("ID");
linesTable.setFromFields("ID");

// link tables
linesTable.setLink(headerTable);

This means the following:

  1. Assign the table INVOICES as source for headerArea.
  2. Assign the table INVOICESLINES as source for linesArea.
  3. area linesArea (subarea) is linked to headerArea (superarea). This means, after each headerArea, the linesArea will be printed.
  4. The field TO (KEY) is the name of the field/s in the subtable (linesTable)
  5. The field FROM (KEY) is the name of the field/s in the supertable (headerTable). You can specifiy several fields separated by "|".
  6. the RJDBCSource in linesArea must be linked to the RJDBCSource in headerArea.

You can also use parameters in your SQL statement. For example:

myJDBCSource=new RJDBCSource(statement, "SELECT * FROM INVOICES where IDate>'[%dateParam]'");

in this case you must provide a value for the parameter before you run the report:

myJDBCSource.setParameter("dateParam","01/01/2001");

If you loaded your report from a template file (REP file), the correct way to set the parameters is:

((RJDBCSource) myreport.getAreaByName("areaname").getDataSource()).setParameter("dateParam","01/01/2001");

 

Printing a JTable

If you want to print a JTable you don‘t have to define the report’s layout field by field, the RJTable class can do it for you.

This class performs the following tasks:

The following example show how to print a Jtable in 5 minutes:

private static void Example5() {

// example: printing a JTable
Win= new RReportWindow(rep);
Win.show();

javax.swing.JTable dataTable = new javax.swing.JTable(columnsData, columnsNames);

RJTable RT=new RJTable(dataTable,0,0,10,2,1.5);
RT.createAreas();
rep.addArea(RT.getHeaderArea());
rep.addArea(RT.getDetailArea());

rep.prepare();

//print here
rep.printArea(RT.getHeaderArea());
rep.printArea(RT.getDetailArea());

rep.endReport();
Win.refreshPageNumber();

}

You first create the RJTable object and provide some information about the size. Then call the createAreas() method and last you add the new areas to you report.

 

ExportLayer interface

RReport can export reports to PDF, DHTML, csv and more. All classes used for exporting a report implement the ExportLayer interface. This interface has the following methods:

Although the RReport class includes methods for exporting to pdf, dhtml and other, you can also use the generic methods in this way:

  1. Create the export layer. For example:

    CsvLayer layer= new CsvLayer();

  2. run the report as usual (execute the prepare() , endReport() methods and so on).
  3. call the export(layer) method of rreport.
  4. depending on the layer you might need to read the result. For example the CsvLayer has a method called getOutput(), while the PDFLayer writes the result directly into a file.

Creating DHTML

RReport can export your report to DHTML. This is usefull if you are using rreport in a web environment. We advise you to use DHTML instead of HTML because it produces better quality output.

In order to export to DHTML you must call the following methods:

rep.setHTMLActive(true); // active HTML output
rep.disablePrinting(true); // do not send output to printer

/ / print report now
rep.prepare();
....
rep.endReport();

// save DHTML output to file
String htmlString=rep.getHTML();
try {

java.io.OutputStreamWriter out2= new java.io.OutputStreamWriter(new java.io.FileOutputStream(fileName),System.getProperty("file.encoding"));
out2.write(htmlString,0,htmlString.length());
out2.close();

} catch (Exception e) { e.printStackTrace(); }

 

The class DHTMLLayer is in charge of converting the reports to DHTML code.

Whenever you export to DHTML you must take into account that the browser requires all to be stored in files. If you create a chart or a barcode, the resulting image must be stored in a image file. The following properties are used for the configuration of this:

report.exportImagesFormat="jpg"; // store the chart or barcode as jpg file
report.exportDirectory="c:\web\images"; // store the file in this subdirectory
report.imagesHTMLPrefix="images\"; // the resulting DHTML will look like this: <IMG SRC="images/XXXXXX.jpg" >

If you want to create GIF or PNG file you must include the following packages in your classpath:

If you are using a RPicture object for printing images, the "ImageHTMLAddress" property will be used when exporting to DHTML. In RReport Visual Builder the property is called "HTML image".

For example:

picture.ImageHTMLAddress="/images/file.jpg"

will generatee <IMG SRC="/images/file.jpg" > as part of the DHTML code. In the case of RPicture you must place the file in the correct directory, RReport will not create the file.

 

Creating PDF

RReport can export your report to PDF. This is usefull if you are using rreport in a web environment. In order to export to PDF you must call the following methods:


rep.disablePrinting(true); // do not send output to printer

/ / print report now
rep.prepare();
....
rep.endReport();

rep.exportPDF(new java.io.FileOutputStream("rreport.pdf"));

RReport uses a free Java library called iText that creates PDF files. Click here to download the pdf library. You must install the PDF library by including the iText.jar file in your class path or in the same directory as rreport.

The class PDFLayer is in charge of converting your report to PDF using iText.

 

Creating Text Output

The method report.exportTXT() can be used for exporting reports to text format. This method returns a java.util.Vector object that contains the pages of the report. Each page (element of the Vector object) is a String[] object where each item in the array is a line in the page. The following code shows how this method con be used:

rep.disablePrinting(true);
rep.prepare();
....
rep.endReport();


java.util.Vector pages=rep.exportTXT();
java.io.FileOutputStream os=new java.io.FileOutputStream("Report.txt");

for (int i=0;i<pages.size();i++) {
// get page

StringBuffer[] page=(StringBuffer[]) pages.elementAt(i);

// write lines of the page
for (int j=0;j<page.length;j++) os.write(page[j].toString().getBytes());


}

os.close();

Note: in order to get a better layout of the exported report you should design and run the report in text mode by setting "Text Mode=Yes" in the report's properties window of RReport Visual Builder.

Creating Csv

The CsvLayer class implements the ExportLayer interface and can therefore be used for exporting reports to csv in the following way:

CsvLayer layer= new CsvLayer();

rep.disablePrinting(true);
rep.prepare();
rep.endReport();
rep.export(layer);

java.io.FileOutputStream os=new java.io.FileOutputStream("Report.tcsv");

os.write(layer.getOutput().getBytes());

os.close();

The following properties of the CsvLayer class allow you to configurate the output of the csv layer:

If ignoreArea(String areaname) can be used to define areas that should not be exported to csv. You can also set the property "Export=No" in the area's properties window in RReport Visual Builder.

 

Creating Xml

 

The XmlLayer class implements the ExportLayer interface and can therefore be used for exporting reports to xml in the following way:

XmlLayer layer= new XmlLayer(report.getPageWidthPixels(),report.getPageHeightPixels(),report.getTitle());

rep.disablePrinting(true);
rep.prepare();
rep.endReport();
rep.export(layer);


String xmlString= layer.getOutput();
java.io.OutputStreamWriter out2= new java.io.OutputStreamWriter(new java.io.FileOutputStream("report.xml"),System.getProperty("file.encoding"));
out2.write(xmlString,0,xmlString.length());
out2.close();

If ignoreArea(String areaname) can be used to define areas that should not be exported to xml. You can also set the property "Export=No" in the area's properties window in RReport Visual Builder.

Text mode printing

RReport normally uses the java printing api for printing your reports. This will result in a graphical report beeing printed using the operating system printing services. However in some circumstances you may need to print a report in text mode. This will result in a much faster printing specially if you a using an impact printer. Text mode printring does not support graphics. It just supports texts (including italic and bold fonts) and lines.

RReport will export your report to text format and will use the TextPrinter package for sending it directly to the printer.This mean RReport will open the port and talk directly to the printer instead of using the operating system services.

The following properties allows you to configure the text mode printer:

The code for printing in text mode is:

report.setTextMode(true); // enabled text mode
report.disablePrinting(true); // disable java printing
report.setTextModeColumns(80); // page size
report.setTextModeRows(60);
report.setTextModePrinterType("HP-PCL3"); // commands supported by the printer (PCL)
report.setTextModePrinter("PRN:"); // parallel port

report.prepare(); // start report

.....

report.endReport(); // finish report
report.printTexMode();
// print now

Web Reports (Servlets)

If you are developing a web application you can also use RReport to create your reports. The reports can be created as DHTML pages or PDF files. In both cases the result can be displayed in the user's browser.

RReport provides a generic servlet call RReportServlet. The Servlet load a java class that implements the IWebReport interface. This interface is used by the servlet to create and run the report.

The servlet has the following parameters:

The IWebReport interface

As already stated the servlet always loads a java class that implements the IWebReport interface. This interface only has 2 methods:

The servlet performs the following steps:

  1. load the class specified in the REPORT parameter of the servlet
  2. call the createReport() method on the class in order to create the report object.
  3. Activate DHTML or PDF output as needed.
  4. call runReport() method of the class.
  5. Send report output (DHTML or PDF) to the user's browser.

RReport provides a ready to use implementation of IWebReport called "WebReportJDBC" which is used to execute reports whose data is read from a database.

 

The WebReportJDBC class

This class is the defaut implementation of IWebReport. It works the following way:

  1. it loads the report template file (*.rep) specified in the REPORTFILE parameter.
  2. All servlet parameters starting with "PAR_" are forwarded to the RSource objects defined in the template file.
  3. It runs the report by calling prepare() and endReport().

This class is used to load and execute reports that can read data from database. The SQL statements in the template file can contain parameters.

For example, suppose you have a report that prints employee's information. Your template file could use the following SQL statement in order to read the employee's data:

Select * from Employees where EmployeeId=[%Id]

Then the servlet should have a parameter called "PAR_ID" which provides the value for the %Id% parameter in the SQL.

You would for example, execute the servlet like this:

http://localhost:8080/rreport/servlet/RReportServlet?REPORTFILE=file://employee.rep&PAR_ID=14&FORMAT=PDF

in order to print the information of employee 14.

Installation on Tomcat

In order to install RReportServlet on Tomcat you must follow the following steps:

Now you can test the installation

 

Examples

The following examples are delivered in app.java :

These are examples that programatically define reports that will help you understand how RReport works, but it is not the best way to create reports. Read the RReport Visual Builder documentation in order to see examples of report created with RReport Visual Designer.

The following example are included in this document: a new Robject to print a triangle.

 

Creating your own RObject

 

The following source code creates a new Robject class for printing triangles:

import java.awt.*;

public class RTriangle extends RObject {

// (x1,y1),(x2,y2) and (x3,y3) make the 3 corners
public double x1=0.5;
public double y1=0;
public double x2=0;
public double y2=1;
public double x3=1;
public double y3=1;

public java.awt.Color color=java.awt.Color.black;

public RTriangle(){
constant=true; }

public void print(Graphics g,double px, double py,Object Value) {

int[] X=new int[3];
int[] Y=new int[3];

// convert from CM to pixels
X[0]=(int) (px+(x1*this.resolution));
Y[0]=(int) (py+(y1*this.resolution));
X[1]=(int) (px+(x2*this.resolution));
Y[1]=(int) (py+(y2*this.resolution));
X[2]=(int) (px+(x3*this.resolution));
Y[2]=(int) (py+(y3*this.resolution));

g.setColor(color);
g.drawPolygon(X,Y,3);
}

}

In order to create you own RObject you must extend the RObject class and implement the function:

public void print(Graphics g,double px, double py,Object Value)

you must then draw your object in the graphics context "g" at the position (px, py). The parameter "Value" can be any runtime object you need. For example, in the case of RField, "Value" is the text that should be printed and in the case of RPicture "Value" is the Image to be printed. In the case of RTriangle we don't use that parameter.

See RObject for more information about field you may need to use in your object.

Optionally you can implement the importFile() function if you want your object to be able to read itself from a report definition file:

 

public void importLine(String key,String val) {

super.importLine(key,val);

if (key.compareTo("COLOR")==0) {
this.color=convertColor(val); }

if (key.compareTo("X1")==0) this.x1=new Double(val).doubleValue();
if (key.compareTo("Y1")==0) this.y1=new Double(val).doubleValue();
if (key.compareTo("X2")==0) this.x2=new Double(val).doubleValue();
if (key.compareTo("Y2")==0) this.y2=new Double(val).doubleValue();
if (key.compareTo("X3")==0) this.x3=new Double(val).doubleValue();
if (key.compareTo("Y3")==0) this.y3=new Double(val).doubleValue();
}

 

This function receives a "key" that contains the name of the field read from the file and the value "val". See also Creating your own objects in RReport Visual Builder.

Text wrapping

You can use the properties expand and compress to specify how the Rfield class will behave if the text is too long or too short:

 

Grids and frames

You can very easily draw a frame around the page,an area, or all areas of the same type.

The following example draws a frame around the report’s page:

rep.setPageFrameStyle(new RLineStyle(0.2f,java.awt.Color.black,RLineStyle.LINE_NORMAL));

The following example draws a frame around the report’s header:

PHDR_PurchaseOrder.setFrameType(RArea.FRAME_AREA);

PHDR_PurchaseOrder.setFrameStyle(new RLineStyle(0.2f,java.awt.Color.black,RLineStyle.LINE_NORMAL));

The following example draws a frame around the report’s header

DETAIL_PurchaseOrder.setFrameType(RArea.FRAME_PAGE);

DETAIL_PurchaseOrder.setFrameStyle(new RLineStyle(0.2f,java.awt.Color.black,RLineStyle.LINE_NORMAL));

Note that in this example only one frame for all the lines of the "purchase order" will be created. If we use RArea.FRAME_AREA instead, a frame for each line is created.

If you want to print a table you may also want to print a grid to separate rows and columns inside this table.

DETAIL_PurchaseOrder.setGrid({8,10,12});

DETAIL_PurchaseOrder.setHorizontalGrid(true);

DETAIL_PurchaseOrder.setGridStyle(new RLineStyle(0.2f,java.awt.Color.black,RLineStyle.LINE_NORMAL));

This code will:

If you use the RJTable class to construct your report, you dont have to worry about this. Just call:

MyRJTable.SetHRDFrameStyle(new RLineStyle(0.2f,java.awt.Color.black,RLineStyle.LINE_NORMAL));

MyRJTable.SetLINFrameStyle(new RLineStyle(0.2f,java.awt.Color.black,RLineStyle.LINE_NORMAL));

MyRJTable.SetLINGridFrameStyle(new RLineStyle(0.2f,java.awt.Color.black,RLineStyle.LINE_NORMAL));

To create frames and grid for the table.

 

 

Java and all Java-based marks are trademarks or registered trademarks of Sun Microsystems, Inc. in the U.S. and other countries