标题:如何获取人工打开的Excel对象
只看楼主
easyppt
Rank: 3Rank: 3
等 级:论坛游侠
威 望:1
帖 子:119
专家分:169
注 册:2021-11-24
结帖率:100%
 问题点数:0 回复次数:22 
如何获取人工打开的Excel对象
VFP要控制的的Excel不是VFP打开的,而是人工打开的,能实现吗,怎么获取
搜索更多相关主题的帖子: 获取 VFP Excel 对象 打开 
2022-04-15 15:23
吹水佬
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:432
帖 子:10064
专家分:41463
注 册:2014-5-20
得分:0 
2022-04-15 19:16
csyx
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:29
帖 子:484
专家分:1827
注 册:2018-3-13
得分:0 
GetObject函数在Win7以上有可能失效,上图为证

2022-04-15 21:55
foxfans
Rank: 4
等 级:贵宾
威 望:11
帖 子:90
专家分:278
注 册:2021-10-23
得分:0 
肯定可以的,是你的前面excel文件名没写上。
试试 ?GETOBJECT("excel.xlsx","excel.application")

[此贴子已经被作者于2022-4-15 22:26编辑过]

2022-04-15 22:14
csyx
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:29
帖 子:484
专家分:1827
注 册:2018-3-13
得分:0 
以下是引用foxfans在2022-4-15 22:14:59的发言:

肯定可以的,是你的前面excel文件名没写上。
试试 ?GETOBJECT("excel.xlsx","excel.application")

加上文件名?说明你根本没明白GetObject这个函数的用法,加上文件名的GetObject就跟NewObject的作用一样,是创建另一个Excel实例,去任务管理器里看看吧

[此贴子已经被作者于2022-4-15 23:16编辑过]

2022-04-15 23:14
foxfans
Rank: 4
等 级:贵宾
威 望:11
帖 子:90
专家分:278
注 册:2021-10-23
得分:0 
如果是控制已经打开的excel,为啥要带类名,直接引用即可, cc=GETOBJECT("c:\2.xlsx")


[此贴子已经被作者于2022-4-15 23:43编辑过]

2022-04-15 23:42
easyppt
Rank: 3Rank: 3
等 级:论坛游侠
威 望:1
帖 子:119
专家分:169
注 册:2021-11-24
得分:0 
我的测试结果 和 csyx   说的是一样的:

环境:Win10系统 和Office Excel 2016
测试结果:
1、带文件名,就变成打开了, 而且因为已经人工打开该文件,还会出现错误提示。
2、如果不带文件名,直接  Getobject(,'Excel.application')  获取不到。

也正因为我已经测试了这样的结果,所以才来论坛发帖的。





[此贴子已经被作者于2022-4-16 08:30编辑过]

2022-04-16 08:29
独木星空
Rank: 16Rank: 16Rank: 16Rank: 16
来 自:河北省曲阳县
等 级:版主
威 望:57
帖 子:713
专家分:556
注 册:2016-6-29
得分:0 
扯点闲的,大家发的帖子有截图,我连个截图也做不来,可能自己没有往这里想过,做不出来,也就不奇怪了。

素数问题的解决是我学习编程永恒的动力。
2022-04-16 08:35
csyx
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:29
帖 子:484
专家分:1827
注 册:2018-3-13
得分:0 
这个问题是有实际意义的,例如软件要导出一些统计数据,通常默认有固定的文件夹和文件名,如果恰好手工打开了这个文件,我们的软件以前是提示用户手工关闭它,但我们希望的是在提示后根据我们的选择自动关闭它或取消导出,要做到自动关闭,就需要获取已经打开的Excel对象。虽然在指定文件名时可以改名,但我们不希望有太多的人工干涉,一是操作人员的电脑知识欠缺(年龄等原因,他们工作经验丰富无法替代),二是统计报表太多,最好只保留最后一份正确的
我参与了软件公司就此问题的工作会议,后来经过开发人员的努力成功解决了,我大概说一下产生此问题的原因和解决思路吧
在xp+Office2003时代,基本不会遇到此类问题,因为那时的Excel大都是以单实例方式运行的。6楼同学可能就是单实例模式,因此用带文件名的GetObject不会提示程序已在运行中,你我都是多实例模式,所以会有提示,同样,我们的各部门使用的Excel版本不同,有高有低,运行模式是安装时默认的(也许通过修改注册表啥的可以都修改,但我们不想采纳)
另一个取不到已经打开的Excel对象问题,就涉及到用户权限,这在xp时代也基本不存在。细究起来就很复杂了,涉及到COM基础知识,可以百度下(知乎 COM编程攻略,浏览下第十六章),GetObject可能就是从ROT表中查找运行中Excel对象的,最关键的问题在于ROT是上下文敏感的,换句话说就是进程权限不同是不会共享的,这才是导致GetObject取不到的关键因素
因此,可以说vfp的GetObject函数,不带第一个参数的用法已部分废废了,之所以说部分废废,是因为如果权限一致时是不会有问题的。双击一个xls文件是用当前登录账号的权限打开文件的,而你的vfp却可能运行在管理员权限下(检查下vfp9.exe是否勾选了以管理员身份运行)。我们使用的软件因为会读写注册表的部分敏感区域(好像还有动态注册控件),需要设置成以管理员身份运行,因此才会遇到你提到的情况。弄清楚了为何取不到,也就知道需要避开ROT这个坑,另寻出路曲线救国了
具体的代码我没有,就算我能看到也无权贴出来,只能根据当时的记录把思路贴出来,希望你自己能实现它(这里高手如云,特别是像吹版这样的高手,有这思路写代码实现易如反掌)
先查找特定窗口句柄,所有的Excel都有一个名为Excel7的子窗口,窗口父子关系是 XLMAIN -> XLDESK -> EXCEL7,找到此窗口句柄后,再用AccessibleObjectFromWindow得到工作簿对象,有了Book对象,再访问Excel,Sheet这些对象就是再普通不过的事儿了
啰啰嗦嗦一大堆,希望对你有所帮助
2022-04-16 18:22
吹水佬
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:432
帖 子:10064
专家分:41463
注 册:2014-5-20
得分:0 
回复 9楼 csyx
查看了一下EXCEL2003、2007确是能找到Book对象

2022-04-16 20:24



参与讨论请移步原网站贴子:https://bbs.bccn.net/thread-508849-1-1.html




关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.284859 second(s), 8 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved