SLK>的PLL程序包

发表于:2007-05-25来源:作者:点击数: 标签:oracle程序SLKPLL前言
1 前言 使用 Oracle Developer做系统,最大的恶梦莫过于做报表,使用ReportBuilder做的报表,用户接受程度非常之底;使用OLE生成EXCEL,则需要耗用大量的内存资源,如果系统于BS模式,则使用OLE生成XLS报表成了系统最大的执行隐患。 今天从莫兄关于SLK的文章

  1 前言
  使用OracleDeveloper做系统,最大的恶梦莫过于做报表,使用ReportBuilder做的报表,用户接受程度非常之底;使用OLE生成EXCEL,则需要耗用大量的内存资源,如果系统于BS模式,则使用OLE生成XLS报表成了系统最大的执行隐患。
  今天从莫兄关于SLK的文章中得到启发,如果使用SLK生成XLS报表,再通过Web.Show_Document调用,则可以基本实现OracleDeveloper的报表问题。
  问题是,SLK的相关知识目前较难寻找,对于报表编制人员也较麻烦,于是花了点时间,编制了一个PLL和相关的实例,希望可以为大家的报表编制拓展思路,同时也希望各位同仁可以不断扩充该程序包的功能,使之成为真正实用的SLK文件生成工具。
  
  2 条件与限制
  2.1 根据莫兄的资料显示,SLK不能实现合并单元格、边框线<单实线以外>、底纹<灰色底纹以外>、图形、图表、对象、链接、分页符、工作表属性、打印页面设置...等等,所以报表中若涉及该EXCEL对象,则不用此SLK程序包
  2.2 由于时间关系,目前程序包存在几个问题:垂直对齐未完成、字体设置有限定<宋体8/12/16/26,宋体加粗12/16/24,字体定义需要预定义,目前尚未了解如何直接定义定体>
  2.3 近期内希望可以实现的拓展功能:再做一个程序包,传入SQL语句,自动生成SLK,并在WEB页中直接显示。此时即可实现长久以来的梦想,定义数据源实现动态SQL查询<原来想用JAVABEAN来实现>
  
  点击此处下载armok0196480.rar
  
  我编译了一个6i的包--土拨鼠!!!
  点击此处下载armok0197000.rar
  
  3 代码<考虑许多同仁没有安装DS9i,所以将源代码贴上,以方便大家
  PACKAGE Fmp_SlkReport IS
  -------------------------------------
  --设置创建SLK文件--------------------
  -------------------------------------
  Procedure SP_CreateSlkFile
  (P_SlkFile In Out Text_Io.File_Type --SLK文件对象
  ,P_FileName In VarChar2 --要创建的文件名
  );
  
  -------------------------------------
  --设置关闭SLK文件--------------------
  -------------------------------------
  Procedure SP_CloseSlkFile
  (P_SlkFile In Out Text_Io.File_Type --SLK文件对象
  );
  
  -------------------------------------
  --设置单元格的值---------------------
  -------------------------------------
  Procedure SP_TransValue
  (
  P_SlkFile In Text_Io.File_Type
  ,P_Row In Number --传入行值
  ,P_Col In Number --传入列值
  ,P_Value In Number); --传入要设定的值,数值型
  
  Procedure SP_TransValue
  (
  P_SlkFile In Text_Io.File_Type
  ,P_Row In Number --传入行值
  ,P_Col In Number --传入列值
  ,P_Value In Varchar2); --传入要设定的值,字符型
  
  Procedure SP_TransValue
  (
  P_SlkFile In Text_Io.File_Type
  ,P_Row In Number --传入行值
  ,P_Col In Number --传入列值
  ,P_Value In Date --传入要设定的值,日期型
  ,P_DataFormat In VarChar2:='yyyy.mm.dd'--要转换为日期的格式
  );
  
  -------------------------------------
  --设置边框线,只能是单实线边框-------
  -------------------------------------
  Procedure SP_SetBorder
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_StartCol In Number --传入起始列
  ,P_EndRow In Number --传入终止行
  ,P_EndCol In Number --传入终止列
  );
  
  -------------------------------------
  --设置行高---------------------------
  -------------------------------------
  Procedure SP_SetRowHeight
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_EndRow In Number --传入起始列
  ,P_RowHeight In Number --要设定的高度
  );
  
  -------------------------------------
  --设置列宽---------------------------
  -------------------------------------
  Procedure SP_SetColWidth
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartCol In Number --传入行值
  ,P_EndCol In Number --传入起始列
  ,P_ColWidth In Number --要设定的列宽
  );
  
  -------------------------------------
  --设置水平居中---------------------------
  -------------------------------------
  Procedure SP_SetVerticalAlign
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_StartCol In Number --传入起始列
  ,P_EndRow In Number --传入终止行
  ,P_EndCol In Number --传入终止列
  ,P_Type In Number --居中方式
  );
  
  -------------------------------------
  --设置垂直居中---------------------------
  -------------------------------------
  Procedure SP_SetHorizontalAlign
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_StartCol In Number --传入起始列
  ,P_EndRow In Number --传入终止行
  ,P_EndCol In Number --传入终止列
  ,P_Type In Number --居中方式
  );
  
  -------------------------------------
  --设置字体---------------------------
  -------------------------------------
  Procedure SP_SetFontstype
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_StartCol In Number --传入起始列
  ,P_EndRow In Number --传入终止行
  ,P_EndCol In Number --传入终止列
  ,P_FontType In Varchar2:='A12' --字体名称,值表如下:A8:宋体8;A10:宋体10;A12:宋体12;A16:宋体16;A24:宋体24;B12:宋体加黑12;B16:宋体加黑16;B24:宋体加黑24;
  );
  
  END Fmp_SlkReport;
  PACKAGE Body Fmp_SlkReport IS
  -------------------------------------
  --设置创建SLK文件--------------------
  -------------------------------------
  Procedure SP_CreateSlkFile
  (P_SlkFile In Out Text_Io.File_Type --SLK文件对象
  ,P_FileName In VarChar2 --要创建的文件名
  )
  Is
  Begin
  --创建并打开文件
  P_SlkFile := Text_IO.Fopen(P_FileName, 'W');
  --写入SLK文件头的相关字符
  Text_IO.PUTF(P_SlkFile, 'ID;PWXL;N;E'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;PGeneral'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P0'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P0.00'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P#,##0'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P#,##0.00'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P#,##0;;\-#,##0'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P#,##0;;[Red]\-#,##0'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P#,##0.00;;\-#,##0.00'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P#,##0.00;;[Red]\-#,##0.00'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P"$"#,##0;;"$"\-#,##0'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P"$"#,##0;;[Red]"$"\-#,##0'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P"$"#,##0.00;;"$"\-#,##0.00'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P"$"#,##0.00;;[Red]"$"\-#,##0.00'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P0%'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P0.00%'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P0.00E+00'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P##0.0E+0'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P#\ ?/?'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P#\ ??/??'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pyyyy/m/d'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pd/mmm/yy'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pd/mmm'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pmmm/yy'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Ph:mm\ AM/PM'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Ph:mm:ss\ AM/PM'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Ph:mm'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Ph:mm:ss'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pyyyy/m/d\ h:mm'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pmm:ss'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pmm:ss.0'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P@'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P[h]:mm:ss'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P_ "$"* #,##0_ ;;_ "$"* \-#,##0_ ;;_ "$"* "-"_ ;;_ @_ '|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P_ * #,##0_ ;;_ * \-#,##0_ ;;_ * "-"_ ;;_ @_ '|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P_ "$"* #,##0.00_ ;;_ "$"* \-#,##0.00_ ;;_ "$"* "-"??_ ;;_ @_ '|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P_ * #,##0.00_ ;;_ * \-#,##0.00_ ;;_ * "-"??_ ;;_ @_ '|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P\$#,##0_);;\(\$#,##0\)'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P\$#,##0_);;[Red]\(\$#,##0\)'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P\$#,##0.00_);;\(\$#,##0.00\)'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P\$#,##0.00_);;[Red]\(\$#,##0.00\)'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pm/d/yy'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pyyyy"年"m"月"d"日"'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Ph"时"mm"分"'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Ph"时"mm"分"ss"秒"'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pyyyy"年"m"月"'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;Pm"月"d"日"'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P上午/下午h"时"mm"分"'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;P上午/下午h"时"mm"分"ss"秒"'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;F宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;F宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;F宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;F宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M180'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M160'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M200'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M320'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M480'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M240;SB'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M320;SB'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M480;SB'|| Chr(10));
  /*
  Text_IO.PUTF(P_SlkFile, 'P;F宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;F宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;F宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;F宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M240'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M180'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'P;E宋体;M400'|| Chr(10));
  */
  Text_IO.PUTF(P_SlkFile, 'F;P0;DG0G8;M285'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'B;Y12;X5;D0 0 11 4'|| Chr(10));
  Text_IO.PUTF(P_SlkFile, 'O;L;D;V0;K47;G100 0.001'|| Chr(10));
  End SP_CreateSlkFile;
  
  -------------------------------------
  --设置关闭SLK文件--------------------
  -------------------------------------
  Procedure SP_CloseSlkFile
  (P_SlkFile In Out Text_Io.File_Type --SLK文件对象
  )
  Is
  Begin
  --写入SLK文件结束相关字符
  Text_IO.PUTF(P_SlkFile, 'E'|| Chr(10));
  --关闭文件
  Text_IO.Fclose(P_SlkFile);
  End SP_CloseSlkFile;
  
  -------------------------------------
  --设置单元格的值---------------------
  -------------------------------------
  Procedure SP_TransValue
  (
  P_SlkFile In Text_Io.File_Type
  ,P_Row In Number --传入行值
  ,P_Col In Number --传入列值
  ,P_Value In Number --传入要设定的值,数值型
  )
  Is
  Begin
  --选择要操作的单元格
  Text_IO.PUTF(P_SlkFile, 'C;');
  Text_IO.PutF(P_SlkFile,'Y'|| To_Char(P_Row) ||';');
  Text_Io.PutF(P_SlkFile,'X'|| To_Char(P_Col) ||';');
  --传入数据
  Text_Io.PutF(P_SlkFile,'K'|| To_Char(P_Value));
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End SP_TransValue;
  
  Procedure SP_TransValue
  (
  P_SlkFile In Text_Io.File_Type
  ,P_Row In Number --传入行值
  ,P_Col In Number --传入列值
  ,P_Value In Varchar2 --传入要设定的值,字符型
  )
  Is
  Begin
  --选择要操作的单元格
  Text_IO.PUTF(P_SlkFile, 'C;');
  Text_IO.PutF(P_SlkFile,'Y'|| To_Char(P_Row) ||';');
  Text_Io.PutF(P_SlkFile,'X'|| To_Char(P_Col) ||';');
  --传入数据
  Text_Io.PutF(P_SlkFile,'K"'|| P_Value|| '"');
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End SP_TransValue;
  
  Procedure SP_TransValue
  (
  P_SlkFile In Text_Io.File_Type
  ,P_Row In Number --传入行值
  ,P_Col In Number --传入列值
  ,P_Value In Date --传入要设定的值,日期型
  ,P_DataFormat In VarChar2:='yyyy.mm.dd'--要转换为日期的格式
  )
  Is
  Begin
  --选择要操作的单元格
  Text_IO.PUTF(P_SlkFile, 'C;');
  Text_IO.PutF(P_SlkFile,'Y'|| To_Char(P_Row) ||';');
  Text_Io.PutF(P_SlkFile,'X'|| To_Char(P_Col) ||';');
  --传入数据
  Text_Io.PutF(P_SlkFile,'K"'|| To_Char(P_Value,P_DataFormat)||'"');
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End SP_TransValue;
  
  -------------------------------------
  --设置边框线,只能是单实线边框-------
  -------------------------------------
  Procedure SP_SetBorder
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_StartCol In Number --传入起始列
  ,P_EndRow In Number --传入终止行
  ,P_EndCol In Number --传入终止列
  )
  Is
  L_Row Number;
  L_Col Number;
  Begin
  For L_Row in P_StartRow..P_EndRow loop
  --定义要设置边框线的行
  Text_Io.PutF(P_SlkFile,'C;Y'|| To_Char(L_Row));
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  For L_Col in P_StartCol..P_EndCol loop
  --定义要设置边框线的列
  Text_Io.PutF(P_SlkFile,'F;SLRTBM0;X'|| To_Char(L_Col));
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End Loop;
  End loop;
  End SP_SetBorder ;
  
  -------------------------------------
  --设置行高---------------------------
  -------------------------------------
  Procedure SP_SetRowHeight
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_EndRow In Number --传入起始列
  ,P_RowHeight In Number --要设定的高度
  )
  Is
  L_Row Number;
  Begin
  For L_Row in P_StartRow..P_EndRow loop
  --设置行高
  Text_Io.PutF(P_SlkFile,'F;M'||To_Char(P_RowHeight*20)||';R'|| To_Char(L_Row));
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End Loop;
  End SP_SetRowHeight;
  
  -------------------------------------
  --设置列宽---------------------------
  -------------------------------------
  Procedure SP_SetColWidth
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartCol In Number --传入行值
  ,P_EndCol In Number --传入起始列
  ,P_ColWidth In Number --要设定的列宽
  )
  Is
  Begin
  --设定列宽
  Text_Io.PutF(P_SlkFile,'F;W'||To_Char(P_StartCol)
  || ' ' || To_Char(P_EndCol)
  || ' ' || To_Char(P_ColWidth));
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End SP_SetColWidth;
  
  -------------------------------------
  --设置水平居中---------------------------
  -------------------------------------
  Procedure SP_SetVerticalAlign
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_StartCol In Number --传入起始列
  ,P_EndRow In Number --传入终止行
  ,P_EndCol In Number --传入终止列
  ,P_Type In Number --居中方式
  )
  Is
  L_Row Number;
  L_Col Number;
  Begin
  For L_Row in P_StartRow..P_EndRow loop
  For L_Col in P_StartCol..P_EndCol loop
  --定义要设置水平居中的单元格
  Text_Io.PutF(P_SlkFile,'F;P0;FG0C;Y' || To_Char(L_Row)
  || ';X' || To_Char(L_Col));
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End Loop;
  End loop;
  End SP_SetVerticalAlign;
  
  -------------------------------------
  --设置垂直居中---------------------------
  -------------------------------------
  Procedure SP_SetHorizontalAlign
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_StartCol In Number --传入起始列
  ,P_EndRow In Number --传入终止行
  ,P_EndCol In Number --传入终止列
  ,P_Type In Number --居中方式
  )
  Is
  L_Row Number;
  L_Col Number;
  Begin
  For L_Row in P_StartRow..P_EndRow loop
  For L_Col in P_StartCol..P_EndCol loop
  --定义要设置垂直居中的单元格
  Text_Io.PutF(P_SlkFile,'F;P0;FG0C;Y' || To_Char(L_Row)
  || ';X' || To_Char(L_Col));
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End Loop;
  End loop;
  End SP_SetHorizontalAlign;
  
  -------------------------------------
  --设置字体---------------------------
  -------------------------------------
  Procedure SP_SetFontsType
  (
  P_SlkFile In Text_Io.File_Type
  ,P_StartRow In Number --传入行值
  ,P_StartCol In Number --传入起始列
  ,P_EndRow In Number --传入终止行
  ,P_EndCol In Number --传入终止列
  ,P_FontType In Varchar2:='A12' --字体名称,值表如下:A8:宋体8;A10:宋体10;A12:宋体12;A16:宋体16;A24:宋体24;B12:宋体加黑12;B16:宋体加黑16;B24:宋体加黑24;
  )
  Is
  L_Row Number;
  L_Col Number;
  L_FontType VarChar2(10);
  Begin
  If Upper(P_FontType) ='A8' Then
  L_FontType:='SM7';
  ElsIf Upper(P_FontType) ='A10' Then
  L_FontType:='SM8';
  ElsIf Upper(P_FontType) ='A12' Then
  L_FontType:='SM1';
  ElsIf Upper(P_FontType) ='A16' Then
  L_FontType:='SM9';
  ElsIf Upper(P_FontType) ='A24' Then
  L_FontType:='SM10';
  ElsIf Upper(P_FontType) ='B12' Then
  L_FontType:='SM11';
  ElsIf Upper(P_FontType) ='A16' Then
  L_FontType:='SM12';
  ElsIf Upper(P_FontType) ='A24' Then
  L_FontType:='SM13';
  End If;
  For L_Row in P_StartRow..P_EndRow loop
  For L_Col in P_StartCol..P_EndCol loop
  --定义要设置垂直居中的单元格
  Text_Io.PutF(P_SlkFile,'F;'|| L_FontType ||';Y' || To_Char(L_Row)
  || ';X' || To_Char(L_Col));
  --换行
  Text_Io.PutF(P_SlkFile,Chr(10));
  End Loop;
  End loop;
  End SP_SetFontsType;
  
  END Fmp_SlkReport;

原文转自:http://www.ltesting.net