动态RDLC报表类DynamicReport:数据表节点数据填充
数据表部分是最麻烦的,可以添加多个数据表,可以设置多维表头,可以设置多字段的统计行,不同的列可以采用不同的样式。在传入数据表前需要先传入列样式、多维表头,数据表和统计列是同一时间传入的,页眉和页脚则需要在数据表后传入。
在这里最多可以设置三行表头,从上到下依次是hearderTop、hearderMerge和数据表中的列。表头的样式包含如下几部分:
public string ColoumName { get; set; } //列名
public float ColoumWidth { get; set; } //列宽
public TextAlign TextAlign { get; set; } //对齐
public ConsoleColor ConsoleColor { get; set; } //颜色
public Boolean IsShortDate { get; set; } //显示短日期格式
多维表头的数据表结构是:
DataTable hearderMerge = new DataTable();
hearderMerge.Columns.Add("CellNumber", Type.GetType("System.Int32"));
hearderMerge.Columns.Add("CellValue", Type.GetType("System.String"));
CellNumber代表占用多少列宽度,1为一列,2为合并二列,总列数不能超过或少过数据表的列数;CellValue就是显示的名称。
统计行可以是单列或多列,以string方式传入,不同列用逗号分隔,如“列名1,列名3”,可以是任意列,可以相邻或间隔,但必须是数据表中存在的列并且值可以相加。当只有一列统计时在此列的前面显示“统计:”,如果是第一列则不显示。
数据表会生成DataSets节点和Tablix节点。
private List _coloumStyle = new List();
internal const float ColoumWidth = 1.6F; //列宽
private float tabelTopPosition = 0.0F;
private DataTable hearderName = new DataTable();
private DataTable hearderMerge = new DataTable();
private DataTable hearderTop = new DataTable();
public void SetColoumStyle(List coloumStyle)
{
this._coloumStyle = coloumStyle;
}
public void AddData(DataTable dataTable, string totalColumn)
{
if (dataTable != null && dataTable.Rows.Count > 0)
{
var coloumNames = new List();
foreach (DataColumn dataColumn in dataTable.Columns)
{
var protertyName = dataColumn.ColumnName;
coloumNames.Add(protertyName);
}
AddReportItemPattern(coloumNames.ToArray(), dataTable, totalColumn);
}
}
protected void AddReportItemPattern(string[] coloumNames, dynamic data, string totalColumn = "")
{
StringBuilder fields = new StringBuilder();
StringBuilder coloums = new StringBuilder();
StringBuilder tablixHearders = new StringBuilder();
StringBuilder tablixCells = new StringBuilder();
StringBuilder tablixMembers = new StringBuilder();
float currentNamePrefix = _reportItemPatterns.Count + _reportHeadPatterns.Count + 1;
float tableWidth = 0F;
float dataRows = ((DataTable)data).Rows.Count; //数据行数
int totalNumber = 0;
string totalWidth = "";
string totalCellPattern = "";
string totalMemberPattern = "";
string mergeMemberPattern = "";
Boolean isHearderMerge = true;
float hearderHeight = 0.0F;
foreach (var coloumName in coloumNames)
{
var coloumWidth = ColoumWidth;
var textAlign = TextAlign.Right;
var consoleColor = ConsoleColor.Black;
var isShortDate = false;
var reportColoumStyle = _coloumStyle.FirstOrDefault(r => r.ColoumName == coloumName);
if (reportColoumStyle != null)
{
textAlign = reportColoumStyle.TextAlign;
coloumWidth = reportColoumStyle.ColoumWidth;
consoleColor = reportColoumStyle.ConsoleColor;
isShortDate = reportColoumStyle.IsShortDate;
}
tableWidth += coloumWidth;
if (totalColumn != "")
{
if (totalColumn.Split(',').Length > 1)
{
for (int i = 0; i < totalColumn.Split(',').Length; i++)
{
if (totalColumn.Split(',')[i] == coloumName)
{
if (totalWidth == "")
{
totalWidth = totalNumber.ToString();
}
else
{
totalWidth += "," + totalNumber.ToString();
}
}
}
}
else
{
if (totalColumn == coloumName)
{
totalWidth = totalNumber.ToString();
}
}
}
totalNumber += 1;
var bottomBorder = string.Empty; //每个单元格底部border
if (dataRows == 0)
{
bottomBorder = " ";
}
var coloumValue = coloumName;
if (hearderName.Rows.Count > 0)
{
foreach (DataColumn dc in hearderName.Columns)
{
if (dc.ColumnName == coloumName)
{
if (hearderName.Rows[0][coloumName].ToString().Trim() != "") coloumValue = hearderName.Rows[0][coloumName].ToString();
}
}
}
//例外,如果coloumName包含Coloum之类的字段,则将value设成空
if (coloumName.IndexOf("Column", System.StringComparison.Ordinal) > -1)
{
coloumValue = " ";
}
fields.AppendFormat(
"{0} System.String ",
coloumName);
coloums.AppendFormat("{0}cm ", coloumWidth);
if (hearderMerge.Rows.Count > 0)
{
if (isHearderMerge)
{
hearderHeight += 0.5F;
mergeMemberPattern = "After true ";
if (hearderTop.Rows.Count > 0)
{
hearderHeight += 0.5F;
mergeMemberPattern += "After true ";
}
isHearderMerge = false;
GetHearderMerge(tablixHearders, currentNamePrefix);
}
tablixHearders.AppendFormat("" +
"true true " +
"{2} " +
"Textbox{0}{1} Middle " +
"2pt 2pt 2pt 1pt ",
coloumName, currentNamePrefix, coloumValue, bottomBorder);
}
else
{
tablixHearders.AppendFormat("" +
"true true " +
"{2} " +
"Textbox{0}{1} {3}Middle " +
"2pt 2pt 2pt 1pt ",
coloumName, currentNamePrefix, coloumValue, bottomBorder);
}
//string valueString = "=IIf(IIf(Fields!{0}.Value=\"True\",\"√\", Fields!{0}.Value)=\"False\",\"\",IIf(Fields!{0}.Value=\"True\",\"√\", Fields!{0}.Value))";
string valueString = "=Fields!{0}.Value";
if (isShortDate) valueString = "=FormatDateTime(Fields!{0}.Value,DateFormat.ShortDate)";
tablixCells.AppendFormat(
"true true " +
"" + valueString + " " +
"{0}{1}1 Middle " +
"2pt 2pt 2pt 1pt ",
coloumName, currentNamePrefix, textAlign, consoleColor);
tablixMembers.AppendFormat(" ");
}
if (totalColumn != "")
{
totalCellPattern = "0.5cm \r\n\r\n";
if (totalColumn.Split(',').Length > 1)
{
for (int i = 0; i < totalColumn.Split(',').Length; i++)
{
if (i == 0)
{
for (int n = 0; n < Convert.ToInt32(totalWidth.Split(',')[i]); n++)
{
totalCellPattern += "true true " +
" " +
"total" + _reportItemPatterns.Count.ToString() + i.ToString() + n + " Top " +
"0pt 0pt 2pt 0pt \r\n\r\n";
}
}
else
{
for (int n = 0; n < (Convert.ToInt32(totalWidth.Split(',')[i]) - Convert.ToInt32(totalWidth.Split(',')[i - 1]) - 1); n++)
{
totalCellPattern += "true true " +
" " +
"total" + _reportItemPatterns.Count.ToString() + i.ToString() + n + " Top " +
"0pt 0pt 2pt 0pt \r\n\r\n";
}
}
totalCellPattern += "true true " +
"=Sum(CDec(Fields!" + totalColumn.Split(',')[i] + ".Value)) " +
"totalValue" + _reportItemPatterns.Count.ToString() + i.ToString() + " Top " +
"0pt 2pt 2pt 1pt \r\n\r\n";
}
for (int i = 1; i < (coloumNames.Length - Convert.ToInt32(totalWidth.Split(',')[totalWidth.Split(',').Length - 1])); i++)
{
totalCellPattern += "true true " +
" " +
"totalall" + _reportItemPatterns.Count.ToString() + i.ToString() + " Top " +
"0pt 0pt 2pt 0pt \r\n\r\n";
}
}
else
{
if (Convert.ToInt32(totalWidth) > 0) totalCellPattern += "true true " +
"" + totalString + " " +
"totalname" + _reportItemPatterns.Count.ToString() + " Top " +
"2pt 2pt 3pt 1pt " + totalWidth + " \r\n\r\n";
for (int i = 1; i < Convert.ToInt32(totalWidth); i++)
{
totalCellPattern += " \r\n\r\n";
}
totalCellPattern += "true true " +
"=Sum(CDec(Fields!" + totalColumn + ".Value)) " +
"totalValue" + _reportItemPatterns.Count.ToString() + " Top " +
"0pt 2pt 2pt 1pt \r\n\r\n";
for (int i = 1; i < (coloumNames.Length - Convert.ToInt32(totalWidth)); i++)
{
totalCellPattern += "true true " +
" " +
"total" + _reportItemPatterns.Count.ToString() + i + " Top " +
"0pt 0pt 2pt 0pt \r\n\r\n";
}
}
totalCellPattern += " ";
totalMemberPattern = "Before ";
}
//计算表格应该离左边多少距离
var leftPosition = (pageWidth - tableWidth) / 2;
if (leftPosition < leftMargin / 2) leftPosition = leftMargin / 2;
var dataSetName = string.Format("Data{0}", _reportItemPatterns.Count + _reportHeadPatterns.Count + 1);
var reportItemPattern = new ReportItemPattern();
reportItemPattern.Data = DynamicReportExtension.RemoveZeroData(data);
reportItemPattern.DataSetName = dataSetName;
reportItemPattern.DataSetString =
reportItemPattern.DataSetPattern
.Replace("@DataSetName", dataSetName)
.Replace("@Fields", fields.ToString());
reportItemPattern.TablixString =
reportItemPattern.TablixPattern
.Replace("@DataSetName", dataSetName)
.Replace("@TablixColumns", coloums.ToString())
.Replace("@TablixHeader", tablixHearders.ToString())
.Replace("@TablixCells", tablixCells.ToString())
.Replace("@TablixMember", tablixMembers.ToString())
.Replace("@TotalRow", totalCellPattern.ToString())
.Replace("@MergeMember", mergeMemberPattern.ToString())
.Replace("@TotalMember", totalMemberPattern.ToString())
.Replace("@TopPosition", CaculatePlacePostion().ToString())
.Replace("@LeftPostion", leftPosition.ToString());
//读取行数,如果是空行就加到新的
if (dataRows == 0)
{
_reportHeadPatterns.Add(reportItemPattern);
}
else
{
_reportItemPatterns.Add(reportItemPattern);
}
if (totalCellPattern != "")
{
tabelTopPosition = CaculatePlacePostion() + hearderHeight - 0.3F;
}
else
{
tabelTopPosition = CaculatePlacePostion() + hearderHeight - 0.5F;
}
}
protected float CaculatePlacePostion()
{
//每个数据表的高度
float itemCount = _reportItemPatterns.Count * 2f;
// 每个空表头的高度
float emptyItemCount = _reportHeadPatterns.Count * 0.5f;
return itemCount + emptyItemCount;
}
private void GetHearderMerge(StringBuilder tablixHearders, float currentNamePrefix)
{
string topBorder = "";
if (hearderTop.Rows.Count > 0)
{
topBorder = " ";
for (int i = 0; i < hearderTop.Rows.Count; i++)
{
if ((Int32)hearderTop.Rows[i]["CellNumber"] == 1)
{
tablixHearders.AppendFormat("" +
"true true " +
" " +
"TextboxTop{0}{1} Middle " +
"2pt 2pt 2pt 1pt ",
i, currentNamePrefix);
}
else
{
string borderString = "";
if (hearderTop.Rows[i]["CellValue"].ToString().Trim() == "") borderString = " ";
tablixHearders.AppendFormat("" +
"true true " +
"" + hearderTop.Rows[i]["CellValue"].ToString() + " " +
"TextboxTop{0}{1} " + borderString + "Middle " +
"2pt 2pt 2pt 1pt " + hearderTop.Rows[i]["CellNumber"].ToString() + " ",
i, currentNamePrefix);
for (int n = 1; n < Convert.ToInt32(hearderTop.Rows[i]["CellNumber"]); n++)
{
tablixHearders.AppendFormat(" ");
}
}
}
tablixHearders.AppendFormat("" +
" " +
" " +
" 0.5cm " +
" ");
}
if (hearderMerge.Rows.Count > 0)
{
for (int i = 0; i < hearderMerge.Rows.Count; i++)
{
if ((Int32)hearderMerge.Rows[i]["CellNumber"] == 1)
{
tablixHearders.AppendFormat("" +
"true true " +
" " +
"TextboxMerge{0}{1} " + topBorder + "Middle " +
"2pt 2pt 2pt 1pt ",
i, currentNamePrefix);
}
else
{
tablixHearders.AppendFormat("" +
"true true " +
"" + hearderMerge.Rows[i]["CellValue"].ToString() + " " +
"TextboxMerge{0}{1} " + topBorder + "Middle " +
"2pt 2pt 2pt 1pt " + hearderMerge.Rows[i]["CellNumber"].ToString() + " ",
i, currentNamePrefix);
for (int n = 1; n < Convert.ToInt32(hearderMerge.Rows[i]["CellNumber"]); n++)
{
tablixHearders.AppendFormat(" ");
}
}
}
tablixHearders.AppendFormat(" " +
" " +
" " +
" 0.5cm " +
" ");
}
}
动态RDLC报表(一)
动态RDLC报表(二)
动态RDLC报表(三)
动态RDLC报表(四)
动态RDLC报表(五)
动态RDLC报表(六)
动态RDLC报表(七)
动态RDLC报表完整实例下载