Centering data in crosstab column - jasper-reports

This picture shows a sample of what my columns look like in my crosstab (I have two column groups - in this case a date and status). The date should be centered across the 5 columns and I have set the horizontal to be centered. However, it's only centering it based on the size I have set in iReport. I've tried adjusting the various settings but have been unable to center that first row. I'm using JasperReports 4.0.1.

I know it's a little late, but this is how yo do it:
when you declare the columnGroup element, set the headerPosition attribute to "Stretch". Example:
<columnGroup name="month" height="20" headerPosition="Stretch">
<bucket>
<bucketExpression class="java.lang.String"><![CDATA[$F{month}]]></bucketExpression>
</bucket>
<crosstabColumnHeader>
<cellContents backcolor="#999999" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<textField>
<reportElement style="Crosstab Data Text" x="0" y="0" width="16" height="20"/>
<textElement verticalAlignment="Middle"/>
<textFieldExpression class="java.lang.String"><![CDATA[$V{month}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabColumnHeader>
<crosstabTotalColumnHeader>
<cellContents/>
</crosstabTotalColumnHeader>
Regards,
Damian

Related

How to make different pictures display on jasper report? [duplicate]

This question already has an answer here:
How to I display images next to each other in jasper reports in jaspersoft studio in the detail view without the pages multiplying?
(1 answer)
Closed 2 years ago.
I have a issue where the same picture displays when trying to display three seperate images from a "job card" in this case..
but there are actually three different images on the db
this is my SQL:
select distinct job_card.job_card_name,
job_card.job_number,
job_card.job_type,
job_card.job_card_name,
client_account.account_name,
job_card.punchlist_comments,
"user".name,
job_card.customer_name,
job_card.created_at,
job_card.customer_signature_blob,
job_card.technician_signature_blob,
photograph.photo_blob
from $P!{schemaName}.job_card
left join $P!{schemaName}.photograph on $P!{schemaName}.job_card."_id_" = $P!{schemaName}.photograph.job_cards_fk
left join $P!{schemaName}."user" on $P!{schemaName}."user"."_id_" = $P!{schemaName}.job_card.technicians_fk
left join $P!{schemaName}.asset on $P!{schemaName}.asset."_id_" = $P!{schemaName}.job_card.assets_fk
left join $P!{schemaName}.client_account on $P!{schemaName}.client_account."_id_" = $P!{schemaName}.asset.clientaccounts_fk
where job_card._id_ = $P{job_cardUUID}::uuid
"photograph.photo_blob" being the variable
and this is the jasper elements:
<textElement verticalAlignment="Middle">
<font isBold="true"/>
</textElement>
<text><![CDATA[ Installation pictures ]]></text>
</staticText>
<image>
<reportElement x="0" y="180" width="200" height="124" uuid="8bf21ae9-eec4-4c39-b4c1-4c174ec59aab"/>
<box>
<pen lineWidth="0.25"/>
</box>
<imageExpression><![CDATA[$F{photo_blob}]]></imageExpression>
</image>
<image>
<reportElement x="200" y="180" width="200" height="124" uuid="aa9d55fb-184f-4098-95f8-9de17530c99b"/>
<box>
<pen lineWidth="0.25"/>
</box>
<imageExpression><![CDATA[$F{photo_blob}]]></imageExpression>
</image>
<image>
<reportElement x="400" y="180" width="150" height="124" uuid="64df2d59-4154-4b26-a3d1-3f54f1b54eca"/>
<box>
<pen lineWidth="0.25"/>
</box>
<imageExpression><![CDATA[$F{photo_blob}]]></imageExpression>
</image>
I tried putting this box in the detail band but the page just multiplies by the amount of pictures
You have three repeated pictures because you are using three image elements in the same band at the same time, sharing the same expression i.e $F{photo_blob}.
If you have tree or more different pictures for every job_card._id_ you must create a group, say job_card, and in the group header you put
<text><![CDATA[ Installation pictures ]]></text>
And in the detail band you put
<image>
<reportElement x="0" y="180" width="200" height="124" uuid="8bf21ae9-eec4-4c39-b4c1-4c174ec59aab"/>
<box>
<pen lineWidth="0.25"/>
</box>
<imageExpression><![CDATA[$F{photo_blob}]]></imageExpression>
</image>

How to show column at Crosstab even the data is absent

Do anyone have hints, if I want to create crosstab columns from array, then insert the correction information into the crosstab?
For example, I have a table like below in my DB:
customer ---- activity_date ---- activity|
customer1 ---- 01-01-2016 ---- A|
customer1 ---- 01-03-2016 ---- B|
customer2 ---- 01-01-2016 ---- A|
When users request report from JAN 16 to MAR 16, the report should be shown like below:
customer ---- 01-2016 ---- 02-2016 ---- 03-2016 |
customer1 ---- Activity count: 1 ---- Activity count:0 ---- Activity count:1
customer2 ---- Activity count:1 ---- Activity count:0 ---- Activity count:0
total ---- Activity sum:2 ---- Activity sum:0 ---- Activity count:1
The current problem is that, as there is no data within Feb 2016, the column 02-2016 is missing in the report.
Is there any way (like scriptlet) to create an array as column, then tell the JasperReport the insert correct data when activity_date == column_date?
I'm using Jaspersoft Studio.
To show dates without dates (without activities in your case) you should pass the data with datasource. The JasperReports does not know anything about any ranges of dates or something else. It is just require a data.
The problems
The first problem is to get data in date range even the data is absent
And the second one - is to avoid showing in crosstab 'null' data
Solution
In case using DB you can use outter join and some date range 'generator' to show the data.
We should solve this tasks:
Getting the list of all dates (days) in some period of time. For different RDBMS the syntax will be different.
For PostgreSQL you can find the solution in Getting date list in a range in PostgreSQL post
For MySQL - MySQL how to fill missing dates in range & generate days from date range
For SQL Server - SQL Server: How to select all days in a date range even if no data exists for some days
Using left or right outter join.
Sorting data by date and data you want
In case using JavaBean datasources you hould do the same - add dates you need (without data) and sort data. We can skip implementing the data sorting and ask the JasperReports engine to do it for us.
The crosstab has one 'feature' - we can't hide the row with condition. Even we set all properties for hiding all textFields - the empty row will be drawn. If we try to use a filter on Crosstab our additional rows will be disappear. I think the good idea (in this pitiful situation) is to have special name for such row (we can also replace 0 with something better). In my sample it will be 'Not set'.
The sample
I've used the PostgreSQL in this sample.
The report's template
<?xml version="1.0" encoding="UTF-8"?>
<jasperReport xmlns="http://jasperreports.sourceforge.net/jasperreports" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://jasperreports.sourceforge.net/jasperreports http://jasperreports.sourceforge.net/xsd/jasperreport.xsd" name="crss_dates_group" pageWidth="842" pageHeight="595" orientation="Landscape" whenNoDataType="AllSectionsNoDetail" columnWidth="802" leftMargin="20" rightMargin="20" topMargin="20" bottomMargin="20" isIgnorePagination="true" uuid="6886d70f-dbf3-4dfa-bbee-d5bc70b1c45d">
<style name="Crosstab Data Text" hAlign="Center"/>
<subDataset name="dsDates" uuid="9b8d3c04-25f5-40f0-b116-a77f8d2f7445">
<queryString language="SQL">
<![CDATA[SELECT activityName, to_char(generate_series, 'YYYY-MM-DD') AS activityDate
FROM myTable RIGHT OUTER JOIN (SELECT (generate_series('2010-07-18', '2010-07-29', '1 day'::interval))::date) fake
ON to_char(activityDateFromMyTable, 'YYYY-MM-DD')=to_char(generate_series, 'YYYY-MM-DD') ORDER BY 2, 1]]>
</queryString>
<field name="activityName" class="java.lang.String"/>
<field name="activityDate" class="java.lang.String"/>
<group name="activityDateGroup">
<groupExpression><![CDATA[$F{activityDate}]]></groupExpression>
</group>
</subDataset>
<title>
<band height="79" splitType="Stretch">
<crosstab>
<reportElement x="0" y="0" width="802" height="79" uuid="d39eef3f-aada-406f-99ee-1d2ce2bde5c8"/>
<crosstabDataset>
<dataset>
<datasetRun subDataset="dsDates" uuid="619c0498-512a-4f23-9f1e-6a5d7cfa986d">
<connectionExpression><![CDATA[$P{REPORT_CONNECTION}]]></connectionExpression>
</datasetRun>
</dataset>
</crosstabDataset>
<rowGroup name="activityName" width="95" totalPosition="End">
<bucket class="java.lang.String">
<bucketExpression><![CDATA[$F{activityName}]]></bucketExpression>
</bucket>
<crosstabRowHeader>
<cellContents backcolor="#F0F8FF" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<textField>
<reportElement style="Crosstab Data Text" x="0" y="0" width="95" height="25" uuid="c25490b6-a836-41fb-a36c-a7ebb211bf03"/>
<textFieldExpression><![CDATA[$V{activityName} == null ? "Not set" : $V{activityName}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabRowHeader>
<crosstabTotalRowHeader>
<cellContents backcolor="#BFE1FF" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<staticText>
<reportElement x="0" y="0" width="95" height="25" uuid="12efa463-c4a3-4120-b0e2-0664856cc616"/>
<textElement textAlignment="Center" verticalAlignment="Middle"/>
<text><![CDATA[Total by Date]]></text>
</staticText>
</cellContents>
</crosstabTotalRowHeader>
</rowGroup>
<columnGroup name="activityDate" height="30" totalPosition="End">
<bucket class="java.lang.String">
<bucketExpression><![CDATA[$F{activityDate}]]></bucketExpression>
</bucket>
<crosstabColumnHeader>
<cellContents backcolor="#F0F8FF" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<textField>
<reportElement style="Crosstab Data Text" x="0" y="0" width="61" height="30" uuid="5b931464-5a7a-4e57-a51a-3d687c0a4130"/>
<textFieldExpression><![CDATA[$V{activityDate}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabColumnHeader>
<crosstabTotalColumnHeader>
<cellContents backcolor="#BFE1FF" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<staticText>
<reportElement x="0" y="0" width="50" height="30" uuid="227c77a6-b1c1-485f-95cf-95b43bc95920"/>
<textElement textAlignment="Center" verticalAlignment="Middle"/>
<text><![CDATA[Total by Activity]]></text>
</staticText>
</cellContents>
</crosstabTotalColumnHeader>
</columnGroup>
<measure name="activityNameMeasure" class="java.lang.Integer" calculation="Count">
<measureExpression><![CDATA[$F{activityName}]]></measureExpression>
</measure>
<crosstabCell width="61" height="25">
<cellContents>
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<textField>
<reportElement style="Crosstab Data Text" x="0" y="0" width="61" height="25" uuid="b8a8aacb-58d1-447a-9628-7f045b039f9f"/>
<textFieldExpression><![CDATA[$V{activityNameMeasure}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabCell>
<crosstabCell width="61" height="25" rowTotalGroup="activityName">
<cellContents backcolor="#BFE1FF" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<textField>
<reportElement style="Crosstab Data Text" x="0" y="0" width="61" height="25" uuid="02e88c9a-e9cc-4674-9301-21676d3f33bc"/>
<textFieldExpression><![CDATA[$V{activityNameMeasure}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabCell>
<crosstabCell width="50" columnTotalGroup="activityDate">
<cellContents backcolor="#BFE1FF" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<textField>
<reportElement style="Crosstab Data Text" x="0" y="0" width="50" height="25" uuid="d39d1353-61a6-4041-96d6-2065bae0041b"/>
<textFieldExpression><![CDATA[$V{activityNameMeasure}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabCell>
<crosstabCell rowTotalGroup="activityName" columnTotalGroup="activityDate">
<cellContents backcolor="#BFE1FF" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<textField>
<reportElement style="Crosstab Data Text" x="0" y="0" width="50" height="25" uuid="09aa0d57-5cfa-4e78-af85-0e718c0fee44"/>
<textFieldExpression><![CDATA[$V{activityNameMeasure}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabCell>
</crosstab>
</band>
</title>
</jasperReport>
The result in iReport
Notes:
I've tried to hide empty row (with null) with help of "Remove Line With Blank", "Blank When Null", "Print When Expression" properties without any success. The digging in source codes does not help me too.
You can find more info about similar attempts to hide empty records in crosstab here:
Hide NULL Row Groups
JasperReports
Hide a row in crosstab
how to hide row in crosstab when no data
Crosstab: Suppress Null Column, Keep Row Details
Maybe it is a time to vote for this "new old" feature (hiding empty row) at Jaspersoft/Tibco community :)

How do I change the background color on only the ALL columns and rows for a Crosstab report in JasperReports?

I have created a Crosstab report in JasperReports and would like to add some conditional coloring to only the ALL rows and columns.
So far I have attempted to check for the <Measure>_<Column Group>_ALL variables in a conditional style, but this doesn't work when some of the values are the same as the values in the ALL row/columns.
I am using the ROW_COUNT variable to do alternating row colors, but I noticed that it doesn't count the ALL row as a discrete row.
Is this possible?
I want the background color for the data in the average columns/rows to be grey in the above example without messing up the alternating row color.
To set specific style to a column group it needs to be outside of your datasource. Add a crosstabCell where you set the columnTotalGroup and on this set style as you like.
jrxml code
<crosstabCell width="50" height="28" columnTotalGroup="myColumnGroup">
<cellContents backcolor="#BFE1FF" mode="Opaque">
<box>
<pen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
</box>
<textField>
<reportElement style="Crosstab Data Text" x="0" y="11" width="50" height="16" forecolor="#000000" uuid="27bcff56-8b7a-4867-b1bb-f0f35f750525"/>
<textElement verticalAlignment="Middle">
<font size="8"/>
<paragraph lineSpacing="Single"/>
</textElement>
<textFieldExpression><![CDATA[$V{myAverage})]]></textFieldExpression>
</textField>
</cellContents>
</crosstabCell>
To get the cell's after the data set totalPosition="End" on the group
You can apply this also for rows totals using setRowTotalGroup

Crosstab with no totals

In JasperReports (using Jaspersoft Studio), is there a way to show contents without including totals?
I have the crosstab code here. If I delete the lines were appear <crosstabTotalRowHeader> and <crosstabTotalColumnHeader>, the cross tab keeps showing a total column, the one that does not have a header. I need to delete that column.
<crosstab>
<reportElement x="0" y="0" width="442" height="240" uuid="aae99187-4857-48ad-b2c6-6a66c5e6e89a"/>
<crosstabDataset>
<dataset>
<datasetRun subDataset="grafica_perspectiva" uuid="a819174c-e145-4ad4-a3ef-cddde875ceab">
<connectionExpression><![CDATA[$P{REPORT_CONNECTION}]]></connectionExpression>
</datasetRun>
</dataset>
</crosstabDataset>
<rowGroup name="perspectiva1" width="60" totalPosition="End">
<bucket class="java.lang.String">
<bucketExpression><![CDATA[$F{perspectiva}]]></bucketExpression>
</bucket>
<crosstabRowHeader>
<cellContents mode="Opaque" style="Crosstab_CH">
<textField>
<reportElement x="0" y="0" width="60" height="20" forecolor="#FFFFFF"
uuid="ff8ba239-2c96-4959-8d57-5751f1e67ce1"/>
<textFieldExpression><![CDATA[$V{perspectiva1}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabRowHeader>
<crosstabTotalRowHeader>
<cellContents/>
</crosstabTotalRowHeader>
</rowGroup>
<columnGroup name="cot_nombre1" height="30" totalPosition="End">
<bucket class="java.lang.String">
<bucketExpression><![CDATA[$F{cot_nombre}]]></bucketExpression>
</bucket>
<crosstabColumnHeader>
<cellContents mode="Opaque" style="Crosstab_CH">
<textField>
<reportElement stretchType="RelativeToTallestObject" x="0" y="0" width="140" height="30"
forecolor="#FFFFFF" uuid="76a9a21c-efed-4164-ab6c-4f91e2bf3903"/>
<textFieldExpression><![CDATA[$V{cot_nombre1}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabColumnHeader>
<crosstabTotalColumnHeader>
<cellContents/>
</crosstabTotalColumnHeader>
</columnGroup>
<measure name="promedio_MEASURE1" class="java.lang.String">
<measureExpression><![CDATA[new DecimalFormat("###0.00").format($F{promedio})]]></measureExpression>
</measure>
<crosstabCell width="140" height="20">
<cellContents mode="Opaque" style="Crosstab_CD">
<textField>
<reportElement x="0" y="0" width="140" height="20" uuid="66c4a20e-d1d2-4263-8a1a-19b09f5d93fd"/>
<textFieldExpression><![CDATA[$V{promedio_MEASURE1}]]></textFieldExpression>
</textField>
</cellContents>
</crosstabCell>
<crosstabCell width="140" height="20" rowTotalGroup="perspectiva1">
<cellContents mode="Opaque" style="Crosstab_CD">
<box>
<topPen lineWidth="0.5" lineStyle="Solid" lineColor="#000000"/>
<leftPen lineWidth="0.0" lineStyle="Solid" lineColor="#000000"/>
<bottomPen lineWidth="0.0" lineStyle="Solid" lineColor="#000000"/>
<rightPen lineWidth="0.0" lineStyle="Solid" lineColor="#000000"/>
</box>
</cellContents>
</crosstabCell>
</crosstab>
Never mind. To prevent showing a total column/row in a crosstab, ensure totalPosition attribute in columnGroup/rowGroup is equal to None.
I was looking for a way to do exactly the same thing in Jaspersoft Studio 5.6.
Click on the Crosstab tab beside the Main report tab
Then, in the Outline window for the report, open the crosstab tree and the row groups.
Select the row group you want to set the total position attribute for and set it's value to None in the property window, the cell tab.
Done.

Avoid split of text field to multiple pages

I have a main report and in the main report a sub report called this:
<detail>
<band height="50">
<subreport>
<reportElement x="0" y="1" width="802" height="49" isPrintInFirstWholeBand="true" isPrintWhenDetailOverflows="true"/>
<subreportParameter name="project_id">
<subreportParameterExpression><![CDATA[$P{project_id}]]></subreportParameterExpression>
</subreportParameter>
<connectionExpression><![CDATA[$P{REPORT_CONNECTION}]]></connectionExpression>
<subreportExpression><![CDATA["subs/Project_planned.jasper"]]></subreportExpression>
</subreport>
</band>
</detail>
There is a problem in the subreport because text fields in the detail band are split up on multiple pages what doesn't look very nice. Is there an option to prevent text fields from splitting up to multiple pages when using the property isStretchWithOverflow
Current code of a text field
<textField isStretchWithOverflow="true" isBlankWhenNull="true">
<reportElement stretchType="RelativeToBandHeight" x="555" y="0" width="99" height="21" isPrintInFirstWholeBand="true" forecolor="#000000"/>
<box leftPadding="2">
<topPen lineWidth="1.0" lineColor="#000000"/>
<leftPen lineWidth="1.0" lineColor="#000000"/>
<bottomPen lineWidth="1.0" lineColor="#000000"/>
<rightPen lineWidth="1.0" lineColor="#000000"/>
</box>
<textElement verticalAlignment="Middle">
<paragraph lineSpacing="Single"/>
</textElement>
<textFieldExpression><![CDATA[$F{logic}]]></textFieldExpression>
</textField>
Example on how it looks (sorry for the missing data):
Yes there is, but not on the text field. For the band the text field is in, you can set the Split Type to Prevent. if you set that on the Detail Band and the row needs to overflow to next page, it will move the entire row to the next page.