你好,欢迎来到电脑编程技巧与维护杂志社! 杂志社简介广告服务读者反馈编程社区  
合订本订阅
 
 
您的位置:技术专栏 / 数据库开发
3.11 数据窗口中单元格的屏蔽
 

一、引言

最近接到业务部门的编程需求,给了一张图1所示的Excel表格(税负调查分析户数统计表),共有99行。程序设计好后让基层税务机关进行表格数据的录入,此表格在数据库中每个单位只存一份,发生变动在其上更改即可。其中的要求就是将表格中标有灰色部分的单元格进行屏蔽不允许进行录入。


图1 税负调查分析户数

二、需求分析

通常意义上的屏蔽一般是通过在Datawindow的设计器中将某列的tab属性的值设为0,然后将此字段的背景颜色设置为灰色即可,如图2所示。


图2 属性设置放法

也可以通过程序代码在脚本中进行动态的修改,语法格式如下:

<DW Control Name>.Object.<Columnname>.Protect='<0 - False, 1 - True>'

<DW Control Name>.Object.<Columnname>.Background.Color='<a long>'

命令的具体使用方法这里就不详细介绍了。

如用上面的传统方法进行单元格的屏蔽,在程序设计上是好控制,但要求为每个录入项建立一个字段。我们是不可能为每一个录入项目建立一个字段,像图1所示的表格如果要为每个录入项设计成一个字段则需要使用800多个字段,任何人看到这样的项目都不会愿意这样去进行数据库的设计。显然通过在数据表中一条记录保存一张表格的做法是行不通的。可以将数据库结构设计成下表形式:

表 数据库结构

字段名称

字段代码

字段类型

业务类型代码

YWLX_DM

char(2)

业务类型名称

YWLX_MC

varchar(30)

调查项目代码

DCXM_DM

char(4)

调查项目名称

DCXM_MC

varchar(100)

2005年列入户数

LRHS2005

numeric(6,0)

2004年列入户数

LRHS2004

numeric(6,0)

2005年已调查户数

YDCHS2005

numeric(6,0)

2004年已调查户数

YDCHS2004

numeric(6,0)

操作人员代码

CZRY_DM

varchar(20)

税务机构代码

SWJG_DM

varchar(11)

这种设计让图1表格的每一行变成了数据表中的一条记录。数据库存储的设计问题已经解决,但对于表格中的单元格的屏蔽就不那么好控制了,用上面讲的传统方法就不能进行有效的控制。这是交流和讨论的关键所在。

三、数据库表介绍

我们介绍两个主要表的结构,一个是税负调查分析户数统计表的模板表(BB_SFDCHS_MB);一个是税负调查分析户数统计表(BB_SFDCHS)。这两个表的结构一样但使用的用途不一样。建表脚本如下:

if exists (select 1

            from  sysobjects

            where  id = object_id('dbo.BB_SFDCHS_MB')

            and    type = 'U')

   drop table dbo.BB_SFDCHS_MB

go

PRINT "BB_SFDCHS_MB"

GO

CREATE TABLE dbo.BB_SFDCHS_MB       --税负调查分析户数统计表模板

(

    YWLX_DM     char(2)         NOT NULL,   --业务类型代码    

    YWLX_MC    varchar(30)     NULL,             --业务类型名称

    DCXM_DM   char(4)         NOT NULL,    --业务类型代码

    DCXM_MC    varchar(100)    NULL,            --业务类型名称

    LRHS2005      numeric(6,0)    NULL,         --列入户数2005

    LRHS2004      numeric(6,0)    NULL,         --列入户数2004

    YDCHS2005    numeric(6,0)    NULL,         --已调查户数2005  

    YDCHS2004    numeric(6,0)    NULL,         --已调查户数2004  

    CZRY_DM     varchar(20)     NULL,           --操作人员代码

    SWJG_DM     varchar(11)     NULL,         --税务机构代码

    CONSTRAINT K_BB_SFDCHS_MB

    PRIMARY KEY NONCLUSTERED (YWLX_DM,DCXM_DM)

)

go

if exists (select 1

            from  sysobjects

            where  id = object_id('dbo.BB_SFDCHS')

            and    type = 'U')

   drop table dbo.BB_SFDCHS

go

PRINT "BB_SFDCHS"

GO

CREATE TABLE dbo.BB_SFDCHS      --税负调查分析户数统计表

(

    YWLX_DM     char(2)         NOT NULL,       --业务类型代码     

    YWLX_MC    varchar(30)     NULL,                --业务类型名称

    DCXM_DM    char(4)         NOT NULL,        --业务类型代码

    DCXM_MC    varchar(100)    NULL,            --业务类型名称

    LRHS2005      numeric(6,0)    NULL,         --列入户数2005

    LRHS2004      numeric(6,0)    NULL,         --列入户数2004

    YDCHS2005    numeric(6,0)    NULL,         --已调查户数2005  

    YDCHS2004    numeric(6,0)    NULL,         --已调查户数2004  

    CZRY_DM     varchar(20)     NULL,           --操作人员代码

    SWJG_DM     varchar(11)     NOT NULL,     --税务机构代码

    CONSTRAINT K_BB_SFDCHS

    PRIMARY KEY NONCLUSTERED (SWJG_DM,YWLX_DM,DCXM_DM)

)

Go

这两个表的用途:BB_SFDCHS表存放客户端录入的数据;BB_SFDCHS_MB存放Excel表格的内容。

在图1所示的表格中,将需要屏蔽的单元格的值设置为“888888”(做个标记),注意这里的Excel表格列的顺序一直要和BB_SFDCHS_MB表的结构顺序保持一致,然后将此Excel表格数据另存为文本文件,以使数据快速导入到BB_SFDCHS_MB表中。

 

四、程序设计

创建窗口:w_bb_sfdchs_lr

此窗口主要放置三个数据窗口控件:dw_baobiaodw_mbdw_ylr

对应datawindow名称:d_bb_sfdchsd_bb_sfdchs_mbd_bb_sfdchs

窗口布局如图3所示。


3 窗体布局

1d_bb_sfdchs_mb

数据源为表BB_SFDCHS_MB,对应的SQL

  SELECT BB_SFDCHS.YWLX_DM,  

         BB_SFDCHS.DCXM_DM,  

         BB_SFDCHS.YWLX_MC,  

         BB_SFDCHS.DCXM_MC,  

         BB_SFDCHS.LRHS2005,  

         BB_SFDCHS.LRHS2004,  

         BB_SFDCHS.YDCHS2005,  

         BB_SFDCHS.YDCHS2004,  

         BB_SFDCHS.SWJG_DM,  

         BB_SFDCHS.CZRY_DM 

    FROM BB_SFDCHS 

   WHERE BB_SFDCHS.SWJG_DM = :v_swjg_dm   

2d_bb_sfdchs

数据源为表BB_SFDCHS,对应的SQL

      SELECT BB_SFDCHS_MB.YWLX_DM,  

         BB_SFDCHS_MB.DCXM_DM,  

         BB_SFDCHS_MB.YWLX_MC,  

         BB_SFDCHS_MB.DCXM_MC,  

         BB_SFDCHS_MB.LRHS2005,  

         BB_SFDCHS_MB.LRHS2004,  

         BB_SFDCHS_MB.YDCHS2005,  

         BB_SFDCHS_MB.YDCHS2004,  

         BB_SFDCHS_MB.CZRY_DM,  

         BB_SFDCHS_MB.SWJG_DM 

      FROM BB_SFDCHS_MB  

3.流程讲解

首先dw_mb (模板)数据窗口控件从BB_SFDCHS_MB表中取得数据,然后执行<DW Control Name>.rowscopy()命令将数据拷贝到dw_baobiao中。逐行检查数据列LRHS2005LRHS2004 YDCHS2005 YDCHS2004。如果数据内容等于“888888”则屏蔽此单元格。

用税务机关作为参数,dw_ylr 提取数据表中已录入的数据,如果dw_ylr中存在数据则将数据替换到dw_baobiao中,如无数据则表示没有进行数据录入。

保存数据时,先删除BB_SFDCHS表中对应的数据,然后将dw_baobiao中的数据保存到数据库BB_SFDCHS表中。实现的核心代码及相关说明如下:

//窗口w_bb_sfdchs_lr中定义的Instance 变量:

string is_swjgdm

int LRHS2005[],LRHS2004[],YDCHS2005[],YDCHS2004[]

//窗口w_bb_sfdchs_lropen事件脚本:

dw_mb.settransobject(sqlca)

dw_mb.retrieve()

dw_ylr.settransobject(sqlca)

dw_baobiao.settransobject(sqlca)

//“确定”按钮的clicked事件脚本:

//is_swjgdm 税务机构代码,此窗口定义的instance变量

is_swjgdm=ddlb_swjg_dm.text

if len(is_swjgdm)<1 then

    messagebox("提示","请输入税务机构!")

    return

end if

dw_baobiao.reset()

dw_mb.rowscopy(1,dw_mb.rowcount(),Primary!,dw_baobiao,1,Primary!)

//屏蔽单元格

dw_baobiao.setredraw(FALSE)

dw_baobiao.modify("LRHS2005.background.mode=0")

dw_baobiao.modify("LRHS2004.background.mode=0")

dw_baobiao.modify("#7.background.mode=0")

dw_baobiao.modify("#8.background.mode=0")

int i

int lr05=1,lr04=1,ydc05=1,ydc04=1

//LRHS2005[],LRHS2004[],YDCHS2005[],YDCHS2004[]

for i=1 to dw_baobiao.rowcount()

    if dw_baobiao.GetItemNumber(i,"LRHS2005")=888888 then

       LRHS2005[lr05]=i

        lr05=lr05+1

        dw_baobiao.setItem(i,"LRHS2005",0)

   end if

    if dw_baobiao.GetItemNumber(i,"LRHS2004")=888888 then

       LRHS2004[lr04]=i

        lr04=lr04+1

        dw_baobiao.setItem(i,"LRHS2004",0)

   end if

    if dw_baobiao.GetItemNumber(i,"YDCHS2005")=888888 then

       YDCHS2005[ydc05]=i

        ydc05=ydc05+1

        dw_baobiao.setItem(i,"YDCHS2005",0)

   end if

    if dw_baobiao.GetItemNumber(i,"YDCHS2004")=888888 then

       YDCHS2004[ydc04]=i

        ydc04=ydc04+1

        dw_baobiao.setItem(i,"YDCHS2004",0)

   end if

next

//屏蔽LRHS2005字段

string ls_p

string ls_g

ls_p="LRHS2005.protect='1~tif((getrow()= "

ls_g="LRHS2005.background.color='1000~tif((getrow()="

for i=1 to upperbound(lrhs2005[])

    if i=1 then

    ls_p=ls_p+string(lrhs2005[i])

     ls_g=ls_g+string(lrhs2005[i])

   else

     ls_p=ls_p+" or getrow()="+string(lrhs2005[i])

     ls_g=ls_g+" or getrow()="+string(lrhs2005[i])

   end  if

next

ls_p=ls_p+"),1,0)'"

ls_g=ls_g+ "),rgb(212,208,200),rgb(255,255,255))'"

dw_baobiao.modify(ls_p)

dw_baobiao.modify(ls_g)

//屏蔽LRHS2004字段

ls_p="LRHS2004.protect='1~tif((getrow()= "

ls_g="LRHS2004.background.color='1000~tif((getrow()="

for i=1 to upperbound(LRHS2004[])

    if i=1 then

    ls_p=ls_p+string(LRHS2004[i])

     ls_g=ls_g+string(LRHS2004[i])

   else

     ls_p=ls_p+" or getrow()="+string(LRHS2004[i])

     ls_g=ls_g+" or getrow()="+string(LRHS2004[i])

   end  if

next

ls_p=ls_p+"),1,0)'"

ls_g=ls_g+ "),rgb(212,208,200),rgb(255,255,255))'"

dw_baobiao.modify(ls_p)

dw_baobiao.modify(ls_g)

//屏蔽YDCHS2005字段

ls_p="YDCHS2005.protect='1~tif((getrow()= "

ls_g="#7.background.color='1000~tif((getrow()="

for i=1 to upperbound(YDCHS2005[])

    if i=1 then

    ls_p=ls_p+string(YDCHS2005[i])

     ls_g=ls_g+string(YDCHS2005[i])

   else

     ls_p=ls_p+" or getrow()="+string(YDCHS2005[i])

     ls_g=ls_g+" or getrow()="+string(YDCHS2005[i])

   end  if

next

ls_p=ls_p+"),1,0)'"

ls_g=ls_g+ "),rgb(212,208,200),rgb(255,255,255))'"

dw_baobiao.modify(ls_p)

dw_baobiao.modify(ls_g)

//屏蔽YDCHS2004字段

ls_p="YDCHS2004.protect='1~tif((getrow()= "

ls_g="#8.background.color='1000~tif((getrow()="

for i=1 to upperbound(YDCHS2004[])

    if i=1 then

    ls_p=ls_p+string(YDCHS2004[i])

     ls_g=ls_g+string(YDCHS2004[i])

   else

     ls_p=ls_p+" or getrow()="+string(YDCHS2004[i])

     ls_g=ls_g+" or getrow()="+string(YDCHS2004[i])

   end  if

next

ls_p=ls_p+"),1,0)'"

ls_g=ls_g+ "),rgb(212,208,200),rgb(255,255,255))'"

dw_baobiao.modify(ls_p)

dw_baobiao.modify(ls_g)

dw_baobiao.setredraw(true)

//屏蔽单元格

int li_rowcount

li_rowcount=dw_ylr.retrieve(is_swjgdm)

if dw_ylr.rowcount()<>0 then

    for i=1 to li_rowcount

        dw_baobiao.setitem(i,"lrhs2005",dw_ylr.GetItemNumber(i,"lrhs2005"))

        dw_baobiao.setitem(i,"lrhs2004",dw_ylr.GetItemNumber(i,"lrhs2004"))

        dw_baobiao.setitem(i,"ydchs2005",dw_ylr.GetItemNumber(i,"ydchs2005"))

        dw_baobiao.setitem(i,"ydchs2004",dw_ylr.GetItemNumber(i,"ydchs2004"))

   next    

end if

//“保存”按钮的clicked事件脚本:

long ll_rowcount,ii

ll_rowcount=dw_baobiao.rowcount()

if ll_rowcount=0 then

    return

end if

if dw_baobiao.ModifiedCount()>36 then

    for ii=1 to ll_rowcount

       dw_baobiao.setitem(ii,"swjg_dm",is_swjgdm)

       dw_baobiao.setitem(ii,"czry_dm",gs_czry_dm)

   next

   delete from BB_SFDCHS WHERE SWJG_DM=:is_swjgdm using sqlca;

end if 

if dw_baobiao.update()<>1 then

    rollback;

    messagebox('注意!','存盘未成功,'+sqlca.sqlerrtext,stopsign!)

   return

else

    commit;

    messagebox('注意!','存盘成功!')

end if

保存时先为每一行数据加上单位代码和操作人员代码,删除BB_SFDCHS表中已存的该单位的数据,然后将新数据保存提交到数据库。

//“退出”按钮的clicked事件脚本:

close(parent)

程序代码设计完成后,将数据窗口控件dw_mbdw_ylr的可见属性设置为隐藏。

其中,需要重点理解“确定”按钮的clicked事件的下列代码:

1.刷新设置

dw_baobiao.setredraw(FALSE)

在缺省情况下,PB中的控件在改变属性后,都会进行自动刷新,此代码将刷新设置为FALSE,关闭自动刷新功能。如执行成功则返回1,执行错误则返回-1

2.修改数据窗口列属性

dw_baobiao.modify("LRHS2005.background.mode=0")

dw_baobiao.modify("LRHS2004.background.mode=0")

dw_baobiao.modify("#7.background.mode=0")

dw_baobiao.modify("#8.background.mode=0")

修改数据窗口列属性,将LRHS2005LRHS2004列和第78列的背景模式设置为0,这里一定要设置为不透明模式,否则达不到预想效果。0表示背景为不透明,1表示透明。

也可以使用下面的命令进行修改:

<DW Control Name>.Object.<Columnname>.Background.Mode='<0 - Opaque, 1 - Transparent>'

3.判断单元格内容

//LRHS2005[],LRHS2004[],YDCHS2005[],YDCHS2004[]

for i=1 to dw_baobiao.rowcount()

    if dw_baobiao.GetItemNumber(i,"LRHS2005")=888888 then

       LRHS2005[lr05]=i

        lr05=lr05+1

        dw_baobiao.setItem(i,"LRHS2005",0)

   end if

    if dw_baobiao.GetItemNumber(i,"LRHS2004")=888888 then

       LRHS2004[lr04]=i

        lr04=lr04+1

        dw_baobiao.setItem(i,"LRHS2004",0)

   end if

    if dw_baobiao.GetItemNumber(i,"YDCHS2005")=888888 then

       YDCHS2005[ydc05]=i

        ydc05=ydc05+1

        dw_baobiao.setItem(i,"YDCHS2005",0)

   end if

    if dw_baobiao.GetItemNumber(i,"YDCHS2004")=888888 then

       YDCHS2004[ydc04]=i

        ydc04=ydc04+1

        dw_baobiao.setItem(i,"YDCHS2004",0)

   end if

next

这段代码使用四个数组LRHS2005[]LRHS2004[]YDCHS2005[]YDCHS2004[],采用循环的方式判断单元格的内容是否为“888888”(“888888”是预备屏蔽标记),记录需要进行屏蔽的行号,同时将其值设置为零。

4.屏蔽相应单元格

//屏蔽LRHS2005字段

string ls_p

string ls_g

ls_p="LRHS2005.protect='1~tif((getrow()= "

ls_g="LRHS2005.background.color='1000~tif((getrow()="

for i=1 to upperbound(lrhs2005[])

    if i=1 then

    ls_p=ls_p+string(lrhs2005[i])

     ls_g=ls_g+string(lrhs2005[i])

   else

     ls_p=ls_p+" or getrow()="+string(lrhs2005[i])

     ls_g=ls_g+" or getrow()="+string(lrhs2005[i])

   end  if

   

next

ls_p=ls_p+"),1,0)'"

ls_g=ls_g+ "),rgb(212,208,200),rgb(255,255,255))'"

dw_baobiao.modify(ls_p)

dw_baobiao.modify(ls_g)

我们这里只取出了一个列LRHS2005的屏蔽代码。根据lrhs2005[]数组的记录,屏蔽LRHS2005列中相应的单元格,并将其背景颜色设置成灰色。ls_p变量存放的是屏蔽单元格的代码,ls_g变量存放的是设置单元格背景颜色的代码,通过在程序执行时捕捉到其内容分别为:

LRHS2005.protect='1 if((getrow()= 7 or getrow()=15 or getrow()=18 or getrow()=20 or getrow()=22 or getrow()=23 or getrow()=24 or getrow()=25 or getrow()=26 or getrow()=27 or getrow()=28 or getrow()=29 or getrow()=30 or getrow()=31 or getrow()=32 or getrow()=33 or getrow()=34 or getrow()=35 or getrow()=36 or getrow()=38 or getrow()=39 or getrow()=40 or getrow()=41 or getrow()=42 or getrow()=43 or getrow()=44 or getrow()=45 or getrow()=46 or getrow()=47 or getrow()=48 or getrow()=49 or getrow()=50 or getrow()=51 or getrow()=52 or getrow()=54 or getrow()=55 or getrow()=57 or getrow()=58 or getrow()=59 or getrow()=60 or getrow()=61 or getrow()=62 or getrow()=63 or getrow()=64 or getrow()=65 or getrow()=66 or getrow()=67 or getrow()=68 or getrow()=69 or getrow()=71 or getrow()=72 or getrow()=73 or getrow()=74 or getrow()=76 or getrow()=77 or getrow()=78 or getrow()=80 or getrow()=81 or getrow()=82 or getrow()=83 or getrow()=84 or getrow()=94 or getrow()=95),1,0)'

 

LRHS2005.background.color='1000 if((getrow()=7 or getrow()=15 or getrow()=18 or getrow()=20 or getrow()=22 or getrow()=23 or getrow()=24 or getrow()=25 or getrow()=26 or getrow()=27 or getrow()=28 or getrow()=29 or getrow()=30 or getrow()=31 or getrow()=32 or getrow()=33 or getrow()=34 or getrow()=35 or getrow()=36 or getrow()=38 or getrow()=39 or getrow()=40 or getrow()=41 or getrow()=42 or getrow()=43 or getrow()=44 or getrow()=45 or getrow()=46 or getrow()=47 or getrow()=48 or getrow()=49 or getrow()=50 or getrow()=51 or getrow()=52 or getrow()=54 or getrow()=55 or getrow()=57 or getrow()=58 or getrow()=59 or getrow()=60 or getrow()=61 or getrow()=62 or getrow()=63 or getrow()=64 or getrow()=65 or getrow()=66 or getrow()=67 or getrow()=68 or getrow()=69 or getrow()=71 or getrow()=72 or getrow()=73 or getrow()=74 or getrow()=76 or getrow()=77 or getrow()=78 or getrow()=80 or getrow()=81 or getrow()=82 or getrow()=83 or getrow()=84 or getrow()=94 or getrow()=95),rgb(212,208,200),rgb(255,255,255))'

最后通过dw_baobiao.modify(ls_p)dw_baobiao.modify(ls_g)进行动态地修改。其他三列的代码大同小异不一一讲解了。但一定要记住屏蔽代码的最后一定要执行dw_baobiao.setredraw(true) 恢复刷新模式。

本程序在pb11.0 7549 pb9.0下调试成功。

 

 

 

 

  推荐精品文章

·2024年12月目录 
·2024年11月目录 
·2024年10月目录 
·2024年9月目录 
·2024年8月目录 
·2024年7月目录 
·2024年6月目录 
·2024年5月目录 
·2024年4月目录 
·2024年3月目录 
·2024年2月目录 
·2024年1月目录
·2023年12月目录
·2023年11月目录

  联系方式
TEL:010-82561037
Fax: 010-82561614
QQ: 100164630
Mail:gaojian@comprg.com.cn

  友情链接
 
Copyright 2001-2010, www.comprg.com.cn, All Rights Reserved
京ICP备14022230号-1,电话/传真:010-82561037 82561614 ,Mail:gaojian@comprg.com.cn
地址:北京市海淀区远大路20号宝蓝大厦E座704,邮编:100089