2017-08-21 151 views
1

我有一个模型类,其中包含ZonedDateTime类型的字段。当生成报告的数据显示为:DynamicReports不适用于格式ZonedDateTime

2017-08-17T16:09:03 + 03:00 [欧洲/基希讷乌]

要格式化我使用方法setPattern("dd.MM.yyyy")但没有改变该日期。通过反射产生

所有的东西,检查来源:

for (Field field : entityClass.getDeclaredFields()) { 
    String fieldName = field.getName(); 
    if (usedFields.contains(fieldName)) { 
     field.setAccessible(true); 
     if(field.getType().isAssignableFrom(Date.class) || field.getType().isAssignableFrom(ZonedDateTime.class)){ 
      report.addColumn(Columns.column(fieldName, fieldName, field.getType()).setPattern("dd.MM.yyyy")); 
     }else { 
      report.addColumn(Columns.column(fieldName, fieldName, field.getType())); 
     } 
    } 
} 

生成报告其中列表是元素的泛型列表。

report 
.title(
     Components.text("Documents Report") 
     .setStyle(getHeaderCenteredBoldStyle()) 
     .setHorizontalTextAlignment(HorizontalTextAlignment.CENTER)) 
     .pageFooter(Components.pageXofY()) 
.setColumnTitleStyle(getColumnTitleStyle()) 
.highlightDetailEvenRows() 
.setDataSource(list); 

生成的PDF

generated pdf 任何想法?

+0

实际渲染是做什么的?仅仅调用'toString()'是不够的,你必须格式化你的dateTimes,而你的输出看起来完全像'toString()'结果。 –

+0

@ M.Prokhorov检查更新,我如何格式化这个。日期。我在exaples中找到的所有东西都是* setPattern()*方法。在回答中检查更新 – GVArt

+0

在我看来,你的'DynamicReports'版本不支持'java.time'库。既然您似乎通过反射来构建它,请尝试使用'setPatternExpression'方法来使用适当的格式表达式代码。 –

回答

2

看来setPattern适用于java.util.Date,但不适用于java.time.ZonedDateTime。我创建了一个简单的实体:

public class Entity { 

    private ZonedDateTime zonedDateTime = ZonedDateTime.parse("2017-08-17T16:09:03+03:00[Europe/Chisinau]"); 

    private Date date = new Date(); 

    // getters and setters 
} 

然后我用你的代码(for (Field field : entityClass.getDeclaredFields()) etc)来添加列。对于数据源list,我手动创建它,只是为了测试:

DRDataSource ds = new DRDataSource("zonedDateTime", "date"); 
ds.add(entity.getZonedDateTime(), entity.getDate()); 

在结果报告中,ZonedDateTime未格式化(它显示为2017-08-17T16:09:03+03:00[Europe/Chisinau]),但Date正确地显示为21.08.2017 。来解决这个

的一种方法是设定的值格式并使用java.time.format.DateTimeFormatter转换的ZonedDateTimeString

if (field.getType().isAssignableFrom(ZonedDateTime.class)) { 
    // ZonedDateTime, use a value formatter 
    report.addColumn(Columns.column(fieldName, fieldName, ZonedDateTime.class) 
     // set a custom value formatter 
     .setValueFormatter(new AbstractValueFormatter<String, ZonedDateTime>() { 
      @Override 
      public String format(ZonedDateTime value, ReportParameters reportParameters) { 
       // convert ZonedDateTime to dd.MM.yyyy format 
       DateTimeFormatter fmt = DateTimeFormatter.ofPattern("dd.MM.yyyy"); 
       return value.format(fmt); 
      } 
     })); 
} else if (field.getType().isAssignableFrom(Date.class)) { 
    // java.util.Date: setPattern works 
    report.addColumn(Columns.column(fieldName, fieldName, field.getType()).setPattern("dd.MM.yyyy")); 
... 

由此,ZonedDateTime显示具有在DateTimeFormatter定义的格式:

2017年8月17日

在这个例子中,我在内部类中创建DateTimeFormatter,但最好在if之外创建一个格式化程序(它可以位于static final字段中,因为它是不可变的且线程安全的),并在应用程序中重复使用它。


另一种替代方法是ZonedDateTime手动格式化为String,使用相同的java.time.format.DateTimeFormatter,但在数据源列表。我还不得不改变柱的至String的类型(for内侧):

if (field.getType().isAssignableFrom(ZonedDateTime.class)) { 
    // ZonedDateTime, manually convert to String 
    report.addColumn(Columns.column(fieldName, fieldName, String.class)); 
} else if (field.getType().isAssignableFrom(Date.class)) { 
    // java.util.Date: setPattern works 
    report.addColumn(Columns.column(fieldName, fieldName, field.getType()).setPattern("dd.MM.yyyy")); 
} else { 
    report.addColumn(Columns.column(fieldName, fieldName, field.getType())); 
} 

然后,在数据源list,我不得不使用DateTimeFormatter格式化ZonedDateTimeString

// create formatter 
DateTimeFormatter fmt = DateTimeFormatter.ofPattern("dd.MM.yyyy"); 

// format the ZonedDateTime 
ds.add(entity.getZonedDateTime().format(fmt), entity.getDate()); 

由此,ZonedDateTime现在显示为17.08.2017

我不确定您是如何创建list的值,但您必须将其更改为以上述方式格式化ZonedDateTime(或在内部在实体中执行)。