This sample project shows the possibility of creating a report in runtime with relation and custom object database.

First, create a class of the object that will store the data:
public class ObjectCell {
	public String val;
	
	@Override
	public boolean equals(Object obj) {
		return val.equals(((ObjectCell) obj).val);
	}
	
	public String toString() {
		return val;
	}
	
	public ObjectCell(String val) {
		this.val = val;
	}
}

Next, create the parent database that extends from StiDatabase class and fill data on the connect event:
public class ParentDatabase extends StiDatabase {
	
	public ParentDatabase() {
		super("Demo.Parent"); // Database name
	}
	
	public void connect(StiDataStoreSource stiDataStoreSource, Boolean fillTable) throws StiException {
		DataTable dataTable = stiDataStoreSource.createNewTable();
		for (int i = 0; i < 5; i++) {
			DataRow dataRow = dataTable.createNewRow();
			dataRow.addCell("cId", new ObjectCell("Object" + i));
			dataRow.addCell("cName", "Parent cId: " + i);
		}
		stiDataStoreSource.setDataTable(dataTable);
	}
	
	public void disconnect() {
	}
	
	public void connect(StiDataStoreSource stiDataStoreSource) throws StiException {
		connect(stiDataStoreSource, true);
	}
}

Next, create the same child database:
public class ChildDatabase extends StiDatabase {
	
	public ChildDatabase() {
		super("Demo.Child"); // Database name
	}
	
	public void connect(StiDataStoreSource stiDataStoreSource, Boolean fillTable) throws StiException {
		DataTable dataTable = stiDataStoreSource.createNewTable();
		for (int i = 0; i < 5; i++) {
			for (int k = 0; k < 5; k++) {
				DataRow dataRow = dataTable.createNewRow();
				dataRow.addCell("cId", new ObjectCell("Object" + i));
				for (int j = 1; j < dataRow.getColumns().size(); j++) { // fill row wiht my data
					dataRow.addCell(dataRow.getColumns().get(j).getColumnName(), "Child cId: " + i + " value: " + j);
				}
			}
		}
		stiDataStoreSource.setDataTable(dataTable);
	}
	
	public void disconnect() {
	}
	
	public void connect(StiDataStoreSource stiDataStoreSource) throws StiException {
		connect(stiDataStoreSource, true);
	}
}

To display the report we need to create Java viewer. Create the JFrame, set the necessary options and add the viewer control:
public class CreateRelationsReport extends JPanel {
	
	private static final long serialVersionUID = 330448692680237867L;
	private static final Dimension FRAME_SIZE = new Dimension(800, 800);
	public static void main(final String[] args) {
		SwingUtilities.invokeLater(new Runnable() {
			public void run() {
				try {
					JFrame frame = new JFrame();
					frame.add(new CreateRelationsReport(frame));
					frame.setSize(FRAME_SIZE);
					frame.setLocationRelativeTo(null);
					frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
					frame.setVisible(true);
				} catch (Throwable e) {
					StiExceptionProvider.show(e, null);
				}
			}
		});
	}
	public CreateRelationsReport(final JFrame parentFrame) throws IOException {
		setLayout(new BoxLayout(this, BoxLayout.Y_AXIS));
		setPreferredSize(FRAME_SIZE);
		StiViewerFx viewerPanel = new StiViewerFx(parentFrame);
		add(viewerPanel);

...

Next, create the new report object, then add the parent and child databases to it:
...

		StiReport report = new StiReport();
		
		StiPage page = new StiPage(report);
		report.getPages().add(page);
		page.setName(StiNameCreation.createName(report, StiNameCreation.generateName(page)));
		report.setDictionary(new StiDictionary(report));
		report.getDictionary().getDatabases().add(new ParentDatabase());
		report.getDictionary().getDatabases().add(new ChildDatabase());

...

Next, setup the custom columns in the object table sources:
...

		List<StiDataTableSource> tableSources = new ArrayList<StiDataTableSource>();
		// parent
		StiDataTableSource tSource = new StiDataTableSource("Demo.Parent", "Parent", "Parent");
		tSource.setColumns(new StiDataColumnsCollection());
		tSource.getColumns().add(
			new StiDataColumn("cId", "cId", StiSystemType.getSystemType("System.Object")));
		tSource.getColumns().add(
			new StiDataColumn("cName", "cName", StiSystemType.getSystemType("System.String")));
		tSource.setDictionary(report.getDictionary());
		report.getDictionary().getDataSources().add(tSource);
		tableSources.add(tSource);
		// child
		tSource = new StiDataTableSource("Demo.Child", "Child", "Child");
		tSource.setColumns(new StiDataColumnsCollection());
		tSource.getColumns().add(
			new StiDataColumn("cId", "cId", StiSystemType.getSystemType("System.Object")));
		for (int i = 0; i < 4; i++) {
			tSource.getColumns().add(
				new StiDataColumn("cData" + i, "cData" + i,
				StiSystemType.getSystemType("System.String")));
		}
		tSource.setDictionary(report.getDictionary());
		report.getDictionary().getDataSources().add(tSource);
		tableSources.add(tSource);

...

Add the Header band and Data bands with text boxes to the report:
...

		// Create TitleBand
		StiHeaderBand titleBand = new StiHeaderBand();
		titleBand.setHeight(0.85);
		titleBand.setName("TitleBand");
		page.getComponents().add(titleBand);
		
		// Create Title text on header
		StiText headerText = new StiText(new StiRectangle(0, 0, page.getWidth(), 0.85));
		headerText.setTextInternal("Tacticdescription");
		headerText.setHorAlignment(StiTextHorAlignment.Left);
		headerText.setName("TitleHeader");
		headerText.setFont(new StiFont("Arial", 12F, StiFontStyle.Bold));
		titleBand.getComponents().add(headerText);
		Integer nameIndex = 1;
		List<StiDataBand> dataBands = new ArrayList<StiDataBand>();
		for (StiDataTableSource tableSource : tableSources) {
			// Create Databand
			StiDataBand dataBand = new StiDataBand();
			dataBand.setDataSourceName(tableSource.getName());
			dataBand.setHeight(0.5);
			dataBand.setName("DataBand" + nameIndex);
			nameIndex++;
			page.getComponents().add(dataBand);
			
			double pos = 0;
			double columnWidth = page.getWidth() / tableSource.getColumns().size();
			
			for (StiDataColumn dataColumn : tableSource.getColumns()) {
				StiText dataText = new StiText(new StiRectangle(pos, 0, columnWidth, 0.5));
				dataText.setText("{" + tableSource.getName() + "." + dataColumn.getName() + "}");
				dataText.setName("DataText" + nameIndex.toString());
				dataText.getBorder().setSide(StiBorderSides.All);
				dataBand.getComponents().add(dataText);
				
				pos = pos + columnWidth;
				nameIndex++;
			}
			dataBands.add(dataBand);
		}

...

All components of the report are created, we can now configure the data relations:
...

		dataBands.get(1).setDataRelationName("Relation");
		dataBands.get(1).setMasterComponent(dataBands.get(0));
		
		ArrayList<String> cols = new ArrayList<String>();
		cols.add("cId");
		
		StiDataRelation rel = new StiDataRelation("Relation", tableSources.get(0), tableSources.get(1), cols, cols);
		report.getDictionary().getRelations().add(rel);

...

Finally, render the report and show it in the Java viewer:
...

		report.Render();
		
		viewerPanel.getStiViewModel().getEventDispatcher().dispatchStiEvent(
			new StiViewCommonEvent(StiViewCommonEvent.DOCUMENT_FILE_LOADED,
			new StiDocument(report), null));
	}

In the screenshot below you can see the result of the sample code:

Creating Report with Relations at Runtime

By using this website, you agree to the use of cookies for analytics and personalized content. Cookies store useful information on your computer to help us improve efficiency and usability. For more information, please read the privacy policy and cookie policy.