IDEMPIERE-4868 Implement column lookup support for Jasper Report (#770)

* IDEMPIERE-4868 Implement column lookup support for Jasper Report

add support for more display type

Fix passing of report locale to ColumnLookup and MsgResourceBundle

add alternate short notation for location, account, locator and asi.
This commit is contained in:
hengsin 2021-07-19 17:26:48 +08:00 committed by GitHub
parent 287f41a067
commit e27e11cfce
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 130 additions and 31 deletions

View File

@ -10,6 +10,8 @@ Import-Package: net.sourceforge.barbecue,
org.apache.commons.codec.binary,
org.apache.commons.logging;version="1.1.1",
org.apache.commons.logging.impl;version="1.1.1",
org.jfree.chart,
org.jfree.chart.plot,
org.osgi.service.event
Require-Bundle: org.adempiere.base;bundle-version="0.0.0",
net.sf.jasperreports.engine;bundle-version="6.3.1"

View File

@ -24,30 +24,35 @@
**********************************************************************/
package org.adempiere.report.jasper;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.awt.image.BufferedImage;
import java.math.BigDecimal;
import java.util.function.BiFunction;
import java.util.logging.Level;
import org.adempiere.apps.graph.ChartBuilder;
import org.compiere.model.MAccount;
import org.compiere.model.MAttributeSetInstance;
import org.compiere.model.MChart;
import org.compiere.model.MColumn;
import org.compiere.model.MImage;
import org.compiere.model.MLocation;
import org.compiere.model.MLocator;
import org.compiere.model.MLookup;
import org.compiere.model.MLookupFactory;
import org.compiere.model.MLookupInfo;
import org.compiere.model.MTable;
import org.compiere.util.CLogger;
import org.compiere.util.DB;
import org.compiere.util.DisplayType;
import org.compiere.util.Env;
import org.compiere.util.Language;
import org.compiere.util.NamePair;
import org.compiere.util.Msg;
import org.compiere.util.Util;
import org.jfree.chart.ChartRenderingInfo;
import org.jfree.chart.JFreeChart;
/**
* @author hengsin
*
*/
public class ColumnLookup implements BiFunction<String, Object, String> {
public class ColumnLookup implements BiFunction<String, Object, Object> {
private Language language;
@ -59,7 +64,7 @@ public class ColumnLookup implements BiFunction<String, Object, String> {
}
@Override
public String apply(String t, Object key) {
public Object apply(String t, Object key) {
if (!Util.isEmpty(t, true) && key != null) {
String[] parts = t.split("[.]");
if (parts.length == 2) {
@ -72,41 +77,133 @@ public class ColumnLookup implements BiFunction<String, Object, String> {
if (DisplayType.isList(column.getAD_Reference_ID())) {
MLookupInfo linfo = MLookupFactory.getLookup_List(language, column.getAD_Reference_Value_ID());
MLookup lookup = new MLookup(linfo, -1);
NamePair np = lookup.getDirect(key, false, false);
return np != null ? np.toString() : "";
return lookup.getDisplay(key);
} else if (DisplayType.isLookup(column.getAD_Reference_ID()) && (key instanceof Number)) {
return getLookupDisplay(column, (Number) key);
} else if ((column.getAD_Reference_ID()==DisplayType.ChosenMultipleSelectionList
|| column.getAD_Reference_ID()==DisplayType.ChosenMultipleSelectionSearch
|| column.getAD_Reference_ID()==DisplayType.ChosenMultipleSelectionTable) && (key instanceof String)) {
return getMultiLookupDisplay(column, (String) key);
} else if (DisplayType.Location == column.getAD_Reference_ID() && (key instanceof Number)) {
MLocation loc = MLocation.get(((Number)key).intValue());
return loc.toStringCR();
return getLocation((Number) key);
} else if (DisplayType.Image == column.getAD_Reference_ID() && (key instanceof Number)) {
return getImage(((Number)key).intValue());
} else if (DisplayType.YesNo == column.getAD_Reference_ID() && (key instanceof String)) {
String value = (String) key;
return getYesNoText(value);
} else if (DisplayType.Account == column.getAD_Reference_ID() && (key instanceof Number)) {
return getAccountCombination((Number) key);
} else if (DisplayType.Locator == column.getAD_Reference_ID() && (key instanceof Number)) {
return getLocator((Number) key);
} else if (DisplayType.PAttribute == column.getAD_Reference_ID() && (key instanceof Number)) {
return getAttributeSetInstance((Number) key);
}
}
}
} else if (t.equalsIgnoreCase("location") && (key instanceof Number)) {
return getLocation((Number) key);
} else if (t.equalsIgnoreCase("account") && (key instanceof Number)) {
return getAccountCombination((Number) key);
} else if (t.equalsIgnoreCase("locator") && (key instanceof Number)) {
return getLocator((Number) key);
} else if (t.equalsIgnoreCase("asi") && (key instanceof Number)) {
return getAttributeSetInstance((Number) key);
} else if (t.equalsIgnoreCase("AmtInWords")) {
if (key instanceof String) {
return Msg.getAmtInWords(language, (String) key);
} else if (key instanceof BigDecimal) {
String s = DisplayType.getNumberFormat(DisplayType.Amount, language).format((BigDecimal)key);
return Msg.getAmtInWords(language, s);
}
} else if (t.equalsIgnoreCase("Image") && (key instanceof Number)) {
return getImage(((Number)key).intValue());
} else if (t.equalsIgnoreCase("YesNo") && (key instanceof String)) {
return getYesNoText((String) key);
} else if (t.toLowerCase().startsWith("chart/") && (key instanceof Number)) {
parts = t.split("[/]");
if (parts.length == 3) {
int width = 0;
int height = 0;
try {
width = Integer.parseInt(parts[1]);
height = Integer.parseInt(parts[1]);
} catch (Exception e) {}
if (width > 0 && height > 0) {
return getChartImage(((Number)key).intValue(), width, height);
}
}
return null;
}
}
return "";
}
private Object getAttributeSetInstance(Number key) {
MAttributeSetInstance asi = new MAttributeSetInstance (Env.getCtx(), key.intValue(), null);
if (asi.getM_AttributeSetInstance_ID() > 0)
return asi.getDescription();
else
return "";
}
private Object getLocator(Number key) {
MLocator locator = MLocator.get(key.intValue());
return locator != null ? locator.toString() : "";
}
private Object getAccountCombination(Number key) {
MAccount account = MAccount.get(key.intValue());
return account != null ? account.getCombination() : "";
}
private Object getLocation(Number key) {
MLocation loc = MLocation.get(key.intValue());
return loc.toStringCR();
}
private Object getChartImage(int id, int width, int height) {
MChart mc = new MChart(Env.getCtx(), id, null);
if (mc.get_ID() == id) {
ChartBuilder chartBuilder = new ChartBuilder(mc);
JFreeChart chart = chartBuilder.createChart();
chart.getPlot().setForegroundAlpha(0.8f);
ChartRenderingInfo info = new ChartRenderingInfo();
BufferedImage bi = chart.createBufferedImage(width, height,
BufferedImage.TRANSLUCENT, info);
return bi;
}
return null;
}
private Object getYesNoText(String value) {
if (value.equals("Y")) {
return Msg.getMsg(language, "Yes");
} else if (value.equals("N")) {
return Msg.getMsg(language, "No");
} else {
return "";
}
}
private Object getImage(int key) {
MImage image = MImage.get(key);
return image != null ? image.getImage() : null;
}
private Object getMultiLookupDisplay(MColumn column, String key) {
MLookupInfo mli = MLookupFactory.getLookupInfo(Env.getCtx(), -1, column.getAD_Column_ID(), column.getAD_Reference_ID(), language, column.getColumnName(),
column.getAD_Reference_Value_ID(), false, "");
MLookup lookup = new MLookup(mli, -1);
return lookup.getDisplay(key);
}
private String getLookupDisplay(MColumn column, Number key) {
MLookupInfo mli = MLookupFactory.getLookupInfo(Env.getCtx(), -1, column.getAD_Column_ID(), column.getAD_Reference_ID(), language, column.getColumnName(),
column.getAD_Reference_Value_ID(), false, "");
StringBuilder name = new StringBuilder("");
try (PreparedStatement pstmt = DB.prepareStatement(mli.QueryDirect, null);) {
pstmt.setInt(1, key.intValue());
ResultSet rs = pstmt.executeQuery();
if (rs.next()) {
name.append(rs.getString(3));
boolean isActive = rs.getString(4).equals("Y");
if (!isActive)
name.insert(0, MLookup.INACTIVE_S).append(MLookup.INACTIVE_E);
}
} catch (Exception e) {
CLogger.getCLogger(getClass()).log(Level.SEVERE, e.getMessage(), e);
}
return name.toString();
MLookup lookup = new MLookup(mli, -1);
return lookup.getDisplay(key);
}
}

View File

@ -607,8 +607,7 @@ public class ReportStarter implements ProcessCall, ClientProcess
String langInfo = params.get("AD_Language") != null ? params.get("AD_Language").toString() :
params.get("CURRENT_LANG").toString();
currLang = Language.getLanguage(langInfo);
}
params.put("COLUMN_LOOKUP", new ColumnLookup(currLang));
}
String printerName = null;
MPrintFormat printFormat = null;
@ -643,6 +642,7 @@ public class ReportStarter implements ProcessCall, ClientProcess
params.put("CURRENT_LANG", currLang.getAD_Language());
params.put(JRParameter.REPORT_LOCALE, currLang.getLocale());
params.put("COLUMN_LOOKUP", new ColumnLookup(currLang));
// Resources
File resFile = null;
@ -670,7 +670,7 @@ public class ReportStarter implements ProcessCall, ClientProcess
;
}
}
params.put(JRParameter.REPORT_RESOURCE_BUNDLE, new MsgResourceBundle(res));
params.put(JRParameter.REPORT_RESOURCE_BUNDLE, new MsgResourceBundle(res, currLang.getLocale(), currLang.getAD_Language(), Env.isSOTrx(Env.getCtx())));
Connection conn = null;
JRSwapFileVirtualizer virtualizer = null;