getVolumeInfomation() & SetVolume()(20分)

  • 主题发起人 主题发起人 3h
  • 开始时间 开始时间
3

3h

Unregistered / Unconfirmed
GUEST, unregistred user!
请教这两个函数的用法,例子。
 
hehe,
let me try.
 
3h,

1. GetVolumeInformation的例子: 请打开Delphi下Source/Vcl/fileCtrl.pas,
看一下函数 function VolumeID(DriveChar: Char): string;
2. SetVolumeLabel(不是SetVolume):
function VolumeLabel(DriveChar: Char
NewLabel: String): boolean;
var
OldErrorMode: Integer;
begin
//
OldErrorMode := SetErrorMode(SEM_FAILCRITICALERRORS);
try
result:=SetVolumeLabel(PChar(DriveChar + ':/'), PChar(NewLabel));
finally
SetErrorMode(OldErrorMode);
end;
end;
 
BOOL GetVolumeInformation(
LPCTSTR lpRootPathName, // 指向文件系统根的路径字符串
LPTSTR lpVolumeNameBuffer, // 接收返回的卷名的缓冲区
DWORD nVolumeNameSize, // 上述缓冲区的长度
LPDWORD lpVolumeSerialNumber, // 接收卷序列号的32bit(双字节)整数变量的地址
LPDWORD lpMaximumComponentLength, // 接收卷上最大文件路径长度的32bit(双字节)整数变量的地址
LPDWORD lpFileSystemFlags, // 接收卷文件系统标志的32bit(双字节)整数变量的地址
LPTSTR lpFileSystemNameBuffer, // 接收返回的卷的文件系统名的缓冲区
DWORD nFileSystemNameSize // 上述缓冲区的长度
)


我只想解释一下文件系统标志:
它可以是下列值或它们的组合
FS_CASE_IS_PRESERVED : 保留文件名的大小写
FS_CASE_SENSITIVE : 文件名大小写相关(注意区别和上一个标志的关系)
FS_UNICODE_STORED_ON_DISK : 文件名可以使用Unicode
FS_PERSISTENT_ACLS : 保留并强制使用文件访问控制表(实现文件安全访问控制)
FS_FILE_COMPRESSION : 支持单个文件的压缩
FS_VOL_IS_COMPRESSED : 整个文件卷是压缩的
 
BOOL SetVolumeLabel(
LPCTSTR lpRootPathName, // 指向文件系统根的路径字符串
LPCTSTR lpVolumeName // 卷名字符串
)


For example:
SetVolumeLable(PChar('C:/'), PChar('DelphiWorld'))
 
Examplel of GetVolumeInformation:

var
VolumeNameBuf: array [0..MAX_PATH] of Char;
FSNameBuf: array [0..32] of char;
SerialNo: longInt;
MaxPathLen: longInt;
FSFlag: longint;
begin
GetVolumeInformation(
PChar('C:/'),
VolumeNameBuf,
MAX_PATH
@SerialNo,
@MaxPathLen,
@FSFlag,
FSNameBuf,
32
);

 
多谢你们热心的回答。不过还有点问题请教:

TO pegasus:

我将你写的CUT了,贴到源程序中用,发现有错,要将
GetVolumeInformation( PChar('C:/'),VolumeNameBuf,MAX_PATH,@SerialNo,@MaxPathLen,
@FSFlag,FSNameBuf,32);
中后面两个@去了才没事,什么原因?还有SerialNo:得到一个LONGINT,有什么用?

TO huizhang:
这个TRY和finally是什么作用,怎么查不到?
 
Hi!

You can set you Delphi not to treat pointer restrictly. Then the error
will not occur. (Because the API needs pointer to DWORD, not a pointer
to LongInt, but there's no DWORD in Delphi)
To do this, select your compiler option dialog, then clear "typed @"
option. Or I'll find a better way for you. Are you using Delphi4?

SerialNo is a number generated by Format util, so it can recognize
each volume. Do you remember the old days when using Floppy Disks?
When you change floppy disk, DOS will know this by the serial no
of the disk, :). For there's little chance for two volumes having
the same serial no.

As to "Try" and "Final", it is some advanced function provided by Win32,
that can catch "bugs" or unexpected conditions while the program
running, :).
"Try" begins such catching block. And "Final" just ensure that
no matter what things have happened, the following code MUST be done!
So that you can do some cleanup work there.

Please wait for me to restart my NT so that I can give you a better
solution on the sample code of GetVolumeInfo;
 
hhh,

我用到了 SetErrorMode 函数参数为 SEM_FAILCRITICALERRORS 是为了避免当系统
产生严重错误的时候显示错误信息对话框, 而是将错误信息返回给你的程序
用后
在 finally 将错误处理恢复到系统原来的设置
 
I tested on Delphi 4, the sample procedure should be:

var
VolumeNameBuf: array [0..MAX_PATH] of Char;
FSNameBuf: array [0..32] of char;
SerialNo: longInt;
MaxPathLen: Cardinal;
FSFlag: Cardinal;
begin
GetVolumeInformation( PChar('C:/'),VolumeNameBuf,MAX_PATH, @SerialNo, MaxPathLen,
FSFlag, FSNameBuf,32);
end;

Hehe, Delphi 4 provide new type for Win32, and let it easy to pass
var variable instead of address of variable, :)

Good Luck!
 
huizhang兄:
您好!
您用的OldErrorMode是指发生严重错误时返回来的
错误消息号吗?在那里能察到这些具体的消息?
 
多人接受答案了。
 
后退
顶部