关于VFP网格合计栏
-----在VFP开发中,怎么从未有人提到过关于GRID合计栏显示的问题???
为了合计栏左右随网格滚动,我曾经用两个网格组合类模拟过,效果只能讲马虎。
VFP从3.0到9.0, 从未在这方面改进过,难道这个问题不重要,大家也未提过,不理解?
最后,有无可替代的ACTIVEX网格解决这个问题,前提是能直接连接VFP表。
问题点数:20、回复次数:10Top
1 楼TERRYYRRET(命运)回复于 2006-05-02 21:04:23 得分 0
不明白你说的什么?
合计?先用select生成一张临时表可以吗? 也能实现合计功能啊Top
2 楼YMYANGJIE(呵呵VFP)回复于 2006-05-02 21:18:35 得分 0
不会不明白吧???
难道为了合计必须准备合计行,上下卷动还能看见?Top
3 楼dfwxj(清风)回复于 2006-05-02 21:23:40 得分 0
VFP本身的表格不带合计功能Top
4 楼darkhawlk(黑鹰)回复于 2006-05-02 21:36:06 得分 0
还是用其它控件吧Top
5 楼YMYANGJIE(呵呵VFP)回复于 2006-05-03 09:22:59 得分 0
请各位大侠推荐一款GRID, 要带数据源!!Top
6 楼sdsthgt(老菜)回复于 2006-05-03 17:05:37 得分 0
grid的功能只是显示已有的数据
如果要实现其他功能,请编程,,,
至少我认为是这样!!!!!!!!!!!Top
7 楼YMYANGJIE(呵呵VFP)回复于 2006-05-03 20:39:35 得分 0
呵呵!!
是要编程,组件编程也是编程啊!!Top
8 楼yhlqccnmmt(厚德载物)回复于 2006-05-03 23:24:16 得分 0
upTop
9 楼woxiangfang(小黑黑脸)回复于 2006-05-05 15:22:13 得分 0
我寫過這樣的一段程序,即有橫向合計也有縱向合計,貼出來給大家看看。
我有兩個表﹐都在SQL中﹕一個是T_ORDER﹐另一個是T_ORDERC
其中T_ORDER表中有zzno(單號),zzoperator(操作者),zzorddatet(開單日期)等字段﹐而T_ORDERC中有zzno,zzmainst(主石)等字段。
T_ORDER與T_ORDERC兩表是按T_ZZNO進行關聯的。
現在我要的結果是輸入一個日期﹐然后統計出每月每個人的總數(即T_ORDERC中滿足條件的記錄條數),
每月每個人的間色數(即T_ORDERC中滿足條件的記錄條數﹐只不過﹐此時的條件還要zzmainst='zz')
最后生成的表的結果要如下所示(如我輸入的開始日期為2004年12月20號﹐結束日期為﹕2005年1月5日)
(我生成的表的字段都是要看輸入的日期來自動生成的)﹕
操作者 2004年12月總數 2004年12月間色數 2005年1月總數 2005年1月間色數
... ...... .... .... ....
... ...... .... .... ....
... ...... .... .... ....
IF EMPTY(thisform.text1.Value) OR EMPTY(thisform.text2.Value)
MESSAGEBOX("請輸入訂單起始日",64,"系統提示")
RETURN
ENDIF
mi=MIN(THISFORM.text1.VALUE,THISFORM.text2.VALUE)
ma=MAX(THISFORM.text1.VALUE,THISFORM.text2.VALUE)
thisform.text1.Value=mi
thisform.text2.Value=ma
miyear=year(mi)
mayear=year(ma)
mimon=month(mi)
mamon=month(ma)
nwhere=" zzorddate>='"+DTOC(mi)+"' and zzorddate<='"+DTOC(ma)+"'"
listname="operator c(15),"
nlist=""
mamon=mamon+(mayear-miyear)*12
FOR I=mimon to mamon
listname=listname+"zs"+alltrim(str(I-mimon+1))+" n(6,0),js"+alltrim(str(I-mimon+1))+" n(5,0),"
nlist=nlist+"sum(zs"+alltrim(str(I-mimon+1))+"),sum(js"+alltrim(str(I-mimon+1))+"),"
ENDFOR
listname=listname+"zshj n(7,0),jshj n(6,0)"
nlist=nlist+"sum(zshj) zshj,sum(jshj) jshj"
CREAT CURSOR kdb(&listname)
IF SQLEXEC(connect_sql,"select zzoperator as operator from t_order where "+nwhere,"aa")<0
RETURN
ELSE
SELE kdb
APPE FROM DBF("aa")
ENDIF
nK=1
afieldlist=""
bfieldlist=""
FOR I=mimon to mamon
DIME nArray1(nK),nArray2(nK)
nyear=miyear+iif(I=1,0,int((I-1)/12))
nmonth=iif(I%12=0,12,I%12)
aname="zs"+alltrim(str(I-mimon+1))
bname="js"+alltrim(str(I-mimon+1))
afieldlist=afieldlist+"+"+aname
bfieldlist=bfieldlist+"+"+bname
IF SQLEXEC(connect_sql,"select cast(count_big(*) as int(6)) "+aname+",aa.zzoperator operator from t_order aa,t_orderc bb where aa.zzno=bb.zzno and datepart(year,aa.zzorddate)="+alltrim(str(nyear))+" and datepart(month,aa.zzorddate)="+alltrim(str(nmonth))+" group by aa.zzorddate,aa.zzoperator order by aa.zzorddate,aa.zzoperator","bb")<0
RETURN
ENDIF
SELE BB
INDEX ON operator tag operator
sele kdb
set relation to operator into bb
replace all &aname with bb.&aname
IF SQLEXEC(connect_sql,"select cast(count_big(*) as int(5)) "+bname+",aa.zzoperator operator from t_order aa,t_orderc bb where aa.zzno=bb.zzno and zzmainst='ZZ' and datepart(year,aa.zzorddate)="+alltrim(str(nyear))+" and datepart(month,aa.zzorddate)="+alltrim(str(nmonth))+" group by aa.zzorddate,aa.zzoperator order by aa.zzorddate,aa.zzoperator","cc")<0
RETURN
ENDIF
SELE cc
INDEX ON operator tag operator
sele kdb
set relation to operator into cc
replace all &bname with cc.&bname
nArray1(nK)=alltrim(str(nyear))+"年"+alltrim(str(nmonth))+"月總數"
nArray2(nK)=alltrim(str(nyear))+"年"+alltrim(str(nmonth))+"月間色數"
nK=nK+1
ENDFOR
sele kdb
repl all zshj with &afieldlist,jshj with &bfieldlist
DIME nArray(2*nK+1)
nArray(1)="操作者"
FOR I=1 to nK-1
nArray(2*I)=nArray1(I)
nArray(2*I+1)=nArray2(I)
ENDFOR
nArray(2*I)="總數合計"
nArray(2*I+1)="間色數合計"
sele operator,&nlist from kdb into cursor Temp1 group by operator
AFIELD(nStruArray)
CREAT CURSOR TempInvent FROM ARRAY nStruArray
SELE TempInvent
APPEND FROM DBF('Temp1')
sele "合計 " operator,&nlist from kdb into cursor temp2
scatter to bArray
insert into TempInvent from array bArray
SELE TempInvent
THISFORMSET.FORM4.GRID1.RECORDSOURCE='TempInvent'
THISFORMSET.FORM4.GRID1.COLUMNCOUNT=FCOUN('TempInvent')
FOR I=1 TO FCOUN('TempInvent')
SELE TempInvent
nColumnName='Column'+ALLT(STR(I))
THISFORMSET.FORM4.GRID1.&nColumnName..CONTROLSOURCE=FIELD(I)
THISFORMSET.FORM4.GRID1.&nColumnName..HEADER1.CAPTION=nArray(I)
THISFORMSET.FORM4.GRID1.&nColumnName..WIDTH=MAX(LEN(FIELD(I)),FSIZE(FIELD(I)))*7
IF THISFORMSET.FORM4.GRID1.&nColumnName..WIDTH>240
THISFORMSET.FORM4.GRID1.&nColumnName..WIDTH=240
ENDIF
THISFORMSET.FORM4.GRID1.&nColumnName..HEADER1.ALIGNMENT=2
ENDFOR
SELE TempInvent
GO TOP
WAIT CLEA
THISFORMSET.FORM4.GRID1.SCROLLBARS=3
THISFORMSET.FORM4.CAPTION=THIS.CAPTION
THISFORMSET.FORM1.VISIBLE=.F.
THISFORMSET.FORM4.VISIBLE=.T.Top
10 楼YMYANGJIE(呵呵VFP)回复于 2006-05-05 22:46:51 得分 0
看样子VFP下网格合计确实比较难,要不这么久没有高手出来指点则个;估计主要是网格栏底层绘制事件未公开出来,反之DELPHI下VCL组件机制这些问题就解决得很好。
感谢热心朋友们的回贴,我想让这个贴再放些时候,欢迎继续建议指点。
下面是我作的一个模拟网格合计(类),原理是两个网格组合,合计虚拟网格计算和显示合计栏,HZ_GRID是有一条记录的虚拟数据源,合计栏CONTROLSOURCE是变量数组MCOLUMN1.....MCOLUMNn
整体效果60-70分,无论点击左右滚动栏或者在网格里回车(或TAB),合计栏可以随主网格一起滚动,提供HZ_SUM和HZ_STORE供用户自己控制合计栏和存储合计值。
这个组件原在VFP6.0下作的,作得较粗糙,需要在FORM.PAINT和ACTIVE激活事件、主网格GRID.REFRESH事件写简单代码,封装性太差,严格说还不能算组件,算一个较灵活的解决方法吧。把它贴出来的目的是让VFP爱好者就此发表见解,看能否有更好的控制方法(VF8.0以上支持事件绑定,也许有办法了):
---------------------------------------
INIT()
PUBLIC P_GRDOBJ
P_GRDOBJ = THIS.GRIDSOURCE [THIS.GRIDSOURCE: 父网格设置 ]
SELECT 0
USE .\HZ_GRID
-------------------------------
SETGRID()
PARAMETER V_NAME
LOCAL I , J
IF TYPE(THIS.GRIDSOURCE) <> 'O'
= MESSAGEBOX('...控制源设置错误!!!',48,'错误:')
RETURN .F.
ENDIF
P_GRDOBJ = THIS.GRIDSOURCE
THIS.COLUMNCOUNT=&P_GRDOBJ..COLUMNCOUNT
THIS.RECORDSOURCE = 'HZ_GRID'
THIS.DELETEMARK=&P_GRDOBJ..DELETEMARK
THIS.RECORDMARK=&P_GRDOBJ..RECORDMARK
FOR I = 1 TO THIS.COLUMNCOUNT
MCONTROL = 'MCOLUMN' + ALLTRIM(STR(I))
PUBL &MCONTROL
THIS.COLUMNS(I).VISIBLE=&P_GRDOBJ..COLUMNS(I).VISIBLE
THIS.COLUMNS(I).WIDTH=&P_GRDOBJ..COLUMNS(I).WIDTH
THIS.COLUMNS(I).COLUMNORDER=&P_GRDOBJ..COLUMNS(I).COLUMNORDER
THIS.COLUMNS( I ).ENABLED = .F.
THIS.COLUMNS( I ).SPARSE = .F.
THIS.COLUMNS( I ).CONTROLSOURCE = 'MCOLUMN' + ALLTRIM(STR(I))
THIS.COLUMNS( I ).TEXT1.DISABLEDFORECOLOR = THIS.FORERGB
THIS.COLUMNS( I ).TEXT1.DISABLEDBACKCOLOR = THIS.BACKRGB
THIS.COLUMNS( I ).TEXT1.FORECOLOR = THIS.FORERGB
THIS.COLUMNS( I ).TEXT1.BACKCOLOR = THIS.BACKRGB
THIS.COLUMNS( I ).TEXT1.FORMAT = 'Z'
THIS.COLUMNS(I).COMMENT=&P_GRDOBJ..COLUMNS(I).CONTROLSOURCE
***** WAIT WINDOW THIS.COLUMNS(I).COMMENT+"="+STR(I)[调试时用]
DO CASE
CASE TYPE(THIS.COLUMNS(I).COMMENT) = 'N'
STOR 0 TO &MCONTROL
CASE TYPE(THIS.COLUMNS(I).COMMENT) = 'C'
STOR "" TO &MCONTROL
OTHERWISE
STOR "" TO &MCONTROL
ENDCASE
IF I = THIS.HJCOLUMN
STOR THIS.HJMC TO &MCONTROL
ENDIF
ENDFOR
THIS.LMAIN=&P_GRDOBJ..LEFTCOLUMN
THIS.LSUB = THIS.LEFTCOLUMN
---------------------------------------------
GR_RESIZE()
LOCAL I , _JS, NLEFT , NLEFT1
P_GRDOBJ = THIS.GRIDSOURCE
IF TYPE(THIS.GRIDSOURCE) = 'O'
IF THIS.COLUMNCOUNT<>&P_GRDOBJ..COLUMNCOUNT
THIS.COLUMNCOUNT=&P_GRDOBJ..COLUMNCOUNT
ENDIF
FOR I=1 TO &P_GRDOBJ..COLUMNCOUNT
IF THIS.COLUMNS(I).WIDTH<>&P_GRDOBJ..COLUMNS(I).WIDTH OR THIS.COLUMNS(I).COLUMNORDER<>&P_GRDOBJ..COLUMNS(I).COLUMNORDER OR THIS.COLUMNS(I).VISIBLE<>&P_GRDOBJ..COLUMNS(I).VISIBLE
THISFORM.LOCKSCREEN = .T.
THIS.COLUMNS(I).VISIBLE=&P_GRDOBJ..COLUMNS(I).VISIBLE
THIS.COLUMNS(I).WIDTH=&P_GRDOBJ..COLUMNS(I).WIDTH
THIS.COLUMNS(I).COLUMNORDER=&P_GRDOBJ..COLUMNS(I).COLUMNORDER
THISFORM.LOCKSCREEN = .F.
ENDIF
ENDFOR
P_GRDOBJ = THIS.GRIDSOURCE
IF THIS.LMAIN<>&P_GRDOBJ..LEFTCOLUMN
_JS = 0
DO WHILE (THIS.LEFTCOLUMN<>&P_GRDOBJ..LEFTCOLUMN AND _JS<40)
IF THIS.LEFTCOLUMN>&P_GRDOBJ..LEFTCOLUMN
THISFORM.LOCKSCREEN = .T.
THIS.ISSCROLL = .F.
THIS.DOSCROLL(4)
THISFORM.LOCKSCREEN = .F.
ELSE
THISFORM.LOCKSCREEN = .T.
THIS.ISSCROLL = .F.
THIS.DOSCROLL(5)
THISFORM.LOCKSCREEN = .F.
ENDIF
_JS = _JS + 1
ENDDO
THIS.LMAIN=&P_GRDOBJ..LEFTCOLUMN
ENDIF
IF THIS.LSUB <> THIS.LEFTCOLUMN
_JS = 0
DO WHILE (THIS.LEFTCOLUMN<>&P_GRDOBJ..LEFTCOLUMN AND _JS<40)
IF THIS.LEFTCOLUMN>&P_GRDOBJ..LEFTCOLUMN
THISFORM.LOCKSCREEN = .T.
THIS.ISSCROLL = .F.
&P_GRDOBJ..DOSCROLL(5)
THISFORM.LOCKSCREEN = .F.
ELSE
THISFORM.LOCKSCREEN = .T.
THIS.ISSCROLL = .F.
&P_GRDOBJ..DOSCROLL(4)
THISFORM.LOCKSCREEN = .F.
ENDIF
_JS = _JS + 1
ENDDO
THIS.LSUB = THIS.LEFTCOLUMN
ENDIF
ENDIF
THIS.ISSCROLL = .T.
------------------------------------------------
SCROLLED()
LPARAMETER NDIRECTION
P_GRDOBJ = THIS.GRIDSOURCE
IF THIS.ISSCROLL AND (THIS.LMAIN<>&P_GRDOBJ..LEFTCOLUMN OR THIS.LSUB<>THIS.LEFTCOLUMN)
THIS.GR_RESIZE()
ENDIF
THIS.ISSCROLL = .T.
----------------------------------
HZ_SUM()
THIS.HZ_STORE
-----------------------------------
DESTROY()
RELEASE ALL LIKE MCOLUMN*
USE IN HZ_GRIDTop




