菜单--“最近打开文件”的全路径显示问题

上岸の鱼 2010-07-05 09:24:16
现在因需要做菜单--最近打开文件的功能。
但遇到的问题是:
在使用菜单功能“打开”、“新建”、“另存为”之后,会导致最近打开文件原本显示的全路径消失,只剩下了名称,这让我很郁闷,我想做的是想visual studio的最近打开工程或文件菜单功能那样,可以一直显示全路径的。(包括例如D:\\FOLDER...\\MYPROJECT.SLN这样中间带省略号的,也是我希望允许的。)


我用的系统默认的那个ID_FILE_MRU_RecentList1(记不清了,可能有出入),而是自定义了一个CFileRecentList类, CRecentFileList* m_pRecentListMyFiles; 并添加了UPDATE_COMMAND_UI和ON_COMMAND_EX_RANGE消息响应,以及在相应地方添加的ReadList和WriteList等操作。

基本功能都是好的,就是会遇到上面的无法显示全路径的问题,这个问题在任何一个新建工程的默认“最近打开文件”功能都存在相同问题。

恳请各位高手指点一二,帮小弟解决困难,不胜感激!
...全文
1099 29 打赏 收藏 转发到动态 举报
写回复
用AI写文章
29 条回复
切换为时间正序
请发表友善的回复…
发表回复
bjx_bjx 2010-07-09
  • 打赏
  • 举报
回复
还有一个不推荐的办法,就是在

void CMainFrame::OnUpdateRecentFileList(CCmdUI* pCmdUI)
{
TCHAR szCurDir[_MAX_PATH];
GetCurrentDirectory(_MAX_PATH, szCurDir);
SetCurrentDirectory(_T("C:\\windows"), /*这里写入一个与m_pRecentMyFileList.m_arrNames 数组里任何一个文件不相同的目录*/);
m_pRecentMyFileList.UpdateMenu(pCmdUI);
SetCurrentDirectory(szCurDir);
}

不过这种做法我非常非常的不推荐.可能会引起其他问题.正规的做法是我前边提到的.
bjx_bjx 2010-07-09
  • 打赏
  • 举报
回复
从CRecentFileList派生一个新类重载CRecentFileList::UpdateMenu 函数. 你可以去查看MFC原来的代码,可以原封不动的拷贝过来,在里面有这样一句if (!GetDisplayName(strName, iMRU, szCurDir, nCurDir)) 改成if (!GetDisplayName(strName, iMRU, _T(""), 0)) 就行了 ,或者将上面的GetCurrentDirectory(_MAX_PATH, szCurDir); 改成memset(szCurDir, 0 _MAX_PATH); 都可以.

代码在Microsoft Visual Studio\VC98\MFC\SRC\FILELIST.CPP 你自己可以看一下,想用好MFC就要多跟踪MFC的代码.
上岸の鱼 2010-07-09
  • 打赏
  • 举报
回复
To:bjx_bjx
谢谢你的回答,非常感谢。其实我一直在等你说的SetCurrentDirectory(szCurDir)这样的方法出现,但同时我自己也感觉有些不是很好,如你所说的那样可能会引起其他的一些问题。谢谢你辛苦的回答,虽然得到了一条简单的方法,但我还是会听从你的去从CRecentFileList派生一个新类重载CRecentFileList::UpdateMenu 函数。

这帖子到此就结了。。能得到满意的答案我很开心。非常感谢bjx_bjx(异之意) 的帮助,感谢xianglitian(向立天)的关注,呵呵。
上岸の鱼 2010-07-08
  • 打赏
  • 举报
回复
[Quote=引用 23 楼 bjx_bjx 的回复:]
当前工作路径是 GetCurrentDirectory 得到的结果.
[/Quote]
你说的是对的。。
的确,打开的路径不相同的文件时,原本显示为 test.txt 和 abc.txt的文件时,再打开D:\AnOther Folder\temp.txt时,显示变成:
1 temp.txt
2 D:\My Folder\test.txt
3 D:\My Folder\abc.txt

本来应该算解开小子的疑惑了,但我想能否让当前打开的也显示全路径呢,这样看起来感觉更能一目了然点。我试着在UPDATE_COMMAND_UI的消息函数中进行操作,但没成功,现在的这个消息函数是:
void CMainFrame::OnUpdateRecentFileList(CCmdUI* pCmdUI)
{
m_pRecentMyFileList.UpdateMenu(pCmdUI);
}
能否在这里面进行操作,使第一个temp.txt显示出全路径。

原本我试图通过pCmdUI修改菜单显示的名称,例如修改temp,txt,但第一,路径前面的序号消失了;第二最近打开文件的最后一项菜单会变成跟第一个相同(abc.txt消失了)。所以我修改后的结果就变成了:
D:\AnOther Folder\temp.txt
2 D:\My Folder\test.txt
D:\AnOther Folder\temp.txt

所以还请再劳烦帮我看下
上岸の鱼 2010-07-08
  • 打赏
  • 举报
回复
[Quote=引用 23 楼 bjx_bjx 的回复:]
当前工作路径是 GetCurrentDirectory 得到的结果.
[/Quote]
你说的是对的。。
的确,打开的路径不相同的文件时,原本显示为 test.txt 和 abc.txt的文件时,再打开D:\AnOther Folder\temp.txt时,显示变成:
1 temp.txt
2 D:\My Folder\test.txt
3 D:\My Folder\abc.txt

本来应该算解开小子的疑惑了,但我想能否让当前打开的也显示全路径呢,这样看起来感觉更能一目了然点。我试着在UPDATE_COMMAND_UI的消息函数中进行操作,但没成功,现在的这个消息函数是:
void CMainFrame::OnUpdateRecentFileList(CCmdUI* pCmdUI)
{
m_pRecentMyFileList.UpdateMenu(pCmdUI);
}
能否在这里面进行操作,使第一个temp.txt显示出全路径。

原本我试图通过pCmdUI修改菜单显示的名称,例如修改temp,txt,但第一,路径前面的序号消失了;第二最近打开文件的最后一项菜单会变成跟第一个相同(abc.txt消失了)。所以我修改后的结果就变成了:
D:\AnOther Folder\temp.txt
2 D:\My Folder\test.txt
D:\AnOther Folder\temp.txt

所以还请再劳烦帮我看下

上岸の鱼 2010-07-08
  • 打赏
  • 举报
回复
[Quote=引用 21 楼 xianglitian 的回复:]
引用 20 楼 xx7330842 的回复:
有会的出来溜溜,上论坛就是为了讨论解决问题,顶起,莫沉了!!!!!!!!!!!!!!!!!!!!!!!!!!!!

我不是行家
[/Quote]
不过还是要谢谢你一直来的关注。。呵呵
bjx_bjx 2010-07-08
  • 打赏
  • 举报
回复
当前工作路径是 GetCurrentDirectory 得到的结果.
bjx_bjx 2010-07-08
  • 打赏
  • 举报
回复
[Quote=引用 17 楼 xx7330842 的回复:]
引用 15 楼 bjx_bjx 的回复:
显示的名称是用_AfxAbbreviateName算出来的,其中第二个参数影响输出什么样的格式.既想得到名称的最大允许长度,CRecentFileList里传入的是m_nMaxDisplayLength变量,m_nMaxDisplayLength变量是在CRecentFileList构造时赋值的,你说是你自己的CRecentFileList那么检查构造时……
[/Quote]

很明显,是你 应用程序当前工作路径的原因, 我回复里已经说明了两种因素影响着 最近打开文件菜单 显示的文件名字, 一个是 CRecentFileList 的构造函数 另一个是 你应用程序的当前工作路径,你打开 D:\\My Folder\\abc.txt 文件后,你应用程序的当前路径应该被设置成了D:\\My Folder\\ 而之前列表中的D:\\My Folder\\test.txt文件也同在这个目录下 当然这两个文件都只会显示文件名.

这是从MFC正常的代码分析出来,没看见你的实现代码,所以如果不是两种可能,那建议你 跟踪 CRecentFileList::UpdateMenu 函数, MSDN 我不常来, 有问题请联系我QQ:115385272
向立天 2010-07-08
  • 打赏
  • 举报
回复
[Quote=引用 20 楼 xx7330842 的回复:]
有会的出来溜溜,上论坛就是为了讨论解决问题,顶起,莫沉了!!!!!!!!!!!!!!!!!!!!!!!!!!!!
[/Quote]
我不是行家
chen_freecom 2010-07-08
  • 打赏
  • 举报
回复
MARK.
上岸の鱼 2010-07-08
  • 打赏
  • 举报
回复
有会的出来溜溜,上论坛就是为了讨论解决问题,顶起,莫沉了!!!!!!!!!!!!!!!!!!!!!!!!!!!!
上岸の鱼 2010-07-08
  • 打赏
  • 举报
回复
不会就这么沉下去了吧。。大伙,难道没一个行家?
上岸の鱼 2010-07-07
  • 打赏
  • 举报
回复
[Quote=引用 15 楼 bjx_bjx 的回复:]
显示的名称是用_AfxAbbreviateName算出来的,其中第二个参数影响输出什么样的格式.既想得到名称的最大允许长度,CRecentFileList里传入的是m_nMaxDisplayLength变量,m_nMaxDisplayLength变量是在CRecentFileList构造时赋值的,你说是你自己的CRecentFileList那么检查构造时第五个参数你是否有传值,值为多少,假如 路径……
[/Quote]
首先,感谢你对我问题的回答,但仍存在问题。虽然在程序刚start debugging时是显示全路径的,例如“D:\\My Folder\\test.txt”,打开这个最近文件项后路径也没发生变化;但是在使用“打开”菜单功能打开另一个文件,比如说“D:\\My Folder\\abc.txt”,那么Recent File菜单里显示变成了:
test.txt
abc.txt

我的构造函数是:
CRecentFileList* m_pRecentMyFileList;
m_pRecentMyFileList = new CRecentFileList( 0, _T("My Recent File List"), _T("FilePath%d"), 5, 1000);
所以不是这个1000不够大,还请再看看,帮我解决下
向立天 2010-07-07
  • 打赏
  • 举报
回复
[Quote=引用 15 楼 bjx_bjx 的回复:]
显示的名称是用_AfxAbbreviateName算出来的,其中第二个参数影响输出什么样的格式.既想得到名称的最大允许长度,CRecentFileList里传入的是m_nMaxDisplayLength变量,m_nMaxDisplayLength变量是在CRecentFileList构造时赋值的,你说是你自己的CRecentFileList那么检查构造时第五个参数你是否有传值,值为多少,假如 路径……
[/Quote]
受教
bjx_bjx 2010-07-07
  • 打赏
  • 举报
回复
显示的名称是用_AfxAbbreviateName算出来的,其中第二个参数影响输出什么样的格式.既想得到名称的最大允许长度,CRecentFileList里传入的是m_nMaxDisplayLength变量,m_nMaxDisplayLength变量是在CRecentFileList构造时赋值的,你说是你自己的CRecentFileList那么检查构造时第五个参数你是否有传值,值为多少,假如 路径的 盘符+第一层目录的长度大于了这个值那么只会显示文件名.另外,当前工作目录也会影响显示的是全路径或者缩略名或者是只显示文件名(如果这个文件在当前工作目录下,那么也只会显示文件名).

所以,第一检查你是否有给CRecentFileList的第五个构造参数传值值为多少,第二如果最后打开文件全部在当前工作目录下,那么只显示文件名是很正常的事情.
上岸の鱼 2010-07-07
  • 打赏
  • 举报
回复
[Quote=引用 13 楼 xianglitian 的回复:]
其实我一直没明白
这个菜单项是不是你自己建的啊
如果是那怎么显示应该是你自己控制的啊
如果不是
那你就把原来的删了自己建一个不就好了
[/Quote]
。。。我一直在强调任何新建工程,所以说是一直没动过任何修改,如果你有空帮我看一下,就新建一个SDI工程,使用查看File菜单下的Recent File.随便试一下你就会发现Recent File菜单显示的路径存在我说的显示不全的问题。。
其实我一直纳闷你们怎么会不明白呢,难道“新建一个工程存在这样的问题”这么难理解。
向立天 2010-07-06
  • 打赏
  • 举报
回复
其实我一直没明白
这个菜单项是不是你自己建的啊
如果是那怎么显示应该是你自己控制的啊
如果不是
那你就把原来的删了自己建一个不就好了
上岸の鱼 2010-07-06
  • 打赏
  • 举报
回复
TO:向立天
是的。。是写在注册表的,可能觉得自己说的啰嗦,就简单问:
新建的SDI工程的“最近打开文件”菜单在使用菜单“新建”、“打开”、“另存为”之后导致诸如原本D:\\FOLDER\\MYPROJECT.SLN这样的路径,变成MYPROJECT.SLN这样的。(之于注册表里的仍然是完整的路径)
向立天 2010-07-06
  • 打赏
  • 举报
回复
[Quote=引用 9 楼 xx7330842 的回复:]
引用 8 楼 visualeleven 的回复:
那你自己做一个。。。


自己另做一个是有原因的,因为程序结构要求,把菜单功能都放到了CMainFrame里了。里面不能直接调用APP类的函数。并且关键的是一些信息是写在配置文件里的,所以就自己定义了一个CRecentFileList类
[/Quote]
MFC封装的这个功能路径是写在注册表里的
上岸の鱼 2010-07-06
  • 打赏
  • 举报
回复
UP顶一下,不会没人知道怎么做吧?
加载更多回复(9)

15,979

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 界面
社区管理员
  • 界面
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧