??xml version="1.0" encoding="utf-8" standalone="yes"?>免费精品国产日韩热久久,老男人久久青草av高清,亚洲AV无码一区东京热久久http://www.shnenglu.com/tx7do/category/1514.html严以律己,宽以待h. 三思而后?</br> GMail/GTalk: yanglinbo#google.com;</br> MSN/Email: tx7do#yahoo.com.cn;</br> QQ: 3 0 3 3 9 6 9 2 0 .zh-cnFri, 08 Jun 2012 03:32:31 GMTFri, 08 Jun 2012 03:32:31 GMT60开源日志系llog4cplus(?http://www.shnenglu.com/tx7do/articles/11721.html杨粼?/dc:creator>杨粼?/author>Fri, 25 Aug 2006 20:51:00 GMThttp://www.shnenglu.com/tx7do/articles/11721.htmlhttp://www.shnenglu.com/tx7do/comments/11721.htmlhttp://www.shnenglu.com/tx7do/articles/11721.html#Feedback3http://www.shnenglu.com/tx7do/comments/commentRss/11721.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/11721.html 

l过短暂的熟悉过E,log4cplus已经被成功应用到了我的项目中MQ效果还不错Q:Q除了上文提及的
功能之外Q下面将介绍log4cplus提供的线E和套接字的使用情况?br>

### NDC ###
首先我们先了解一下log4cplus中嵌入诊断上下文QNested Diagnostic ContextQ,即NDC。对logpȝ而言Q?br>当输入源可能不止一个,而只有一个输出时Q往往需要分辩所要输出消息的来源Q比如服务器处理来自不同
客户端的消息时就需要作此判断,NDC可以Z错显C的信息打上一个标?stamp)Q?使得辨认工作看v?br>比较Ҏ些,呵呵。这个标记是U程Ҏ的,利用了线E局部存储机ӞUCؓU程U有数据QThread-specific
 DataQ或TSDQ?看了一下源代码Q相兛_义如下,包括定义、初始化、获取、设|和清除操作Q?/pre>
linux pthread
#   define LOG4CPLUS_THREAD_LOCAL_TYPE pthread_key_t*
#   define LOG4CPLUS_THREAD_LOCAL_INIT ::log4cplus::thread::createPthreadKey()
#   define LOG4CPLUS_GET_THREAD_LOCAL_VALUE( key ) pthread_getspecific(
*key)
#   define LOG4CPLUS_SET_THREAD_LOCAL_VALUE( key, value ) pthread_setspecific(
*key, value)
#   define LOG4CPLUS_THREAD_LOCAL_CLEANUP( key ) pthread_key_delete(
*key)

win32
#   define LOG4CPLUS_THREAD_LOCAL_TYPE DWORD
#   define LOG4CPLUS_THREAD_LOCAL_INIT TlsAlloc()
#   define LOG4CPLUS_GET_THREAD_LOCAL_VALUE( key ) TlsGetValue(key)
#   define LOG4CPLUS_SET_THREAD_LOCAL_VALUE( key, value ) \       TlsSetValue(key, static_cast(value))
#   define LOG4CPLUS_THREAD_LOCAL_CLEANUP( key ) TlsFree(key)
				
使用h比较单,在某个线E中Q?/pre>
    NDC& ndc = log4cplus::getNDC();
    ndc.push(
"ur ndc string");
    LOG4CPLUS_DEBUG(logger, 
"this is a NDC test");
     
    ndc.pop();
        
    LOG4CPLUS_DEBUG(logger, 
"There should be no NDC");
    ndc.remove();


   
当设定输出格?Layout)为TTCCLayoutӞ输出如下Q?/pre>
10-21-04 21:32:58, [3392] DEBUG test  - this is a NDC test
10-21-04 21:32:58, [3392] DEBUG test <> - There should be no NDC...
也可以在自定义的输出格式中用NDC(?x) Q比如:
     
  std::
string pattern = "NDC:[%x]  - %m %n";
  std::auto_ptr _layout(
new PatternLayout(pattern));
     
 LOG4CPLUS_DEBUG(_logger, 
"This is the FIRST log message")
  NDC
& ndc = log4cplus::getNDC();
  ndc.push(
"ur ndc string"); 
  LOG4CPLUS_WARN(_logger, 
"This is the SECOND log message")
  ndc.pop();
 ndc.remove(); 
    

   
输出如下Q?/pre>
NDC:[]  - This is the FIRST log message...
NDC:[ur ndc string]  - This is the SECOND log message...
				
另外一U更单的使用Ҏ是在U程中直接用NDCContextCreatorQ?/pre>
    NDCContextCreator _first_ndc("ur ndc string");
    LOG4CPLUS_DEBUG(logger, 
"this is a NDC test")

   
不必昑ּ地调用push/pop了,而且当出现异常时Q能够确保push与pop的调用是匚w的?/pre>
    
### U程 ###
U程是log4cplus中的副品, 而且仅作了最基本的实玎ͼ使用h也异常简单,只要且必要
在派生类中重载run函数卛_Q?/pre>
class TestThread : public AbstractThread
{
public:
    
virtual void run();
}
;
                
void TestThread::run()

   
/* do sth. */ 
    
}

log4cplus的线E没有考虑同步、死锁,有互斥,实现U程切换的小函数挺别致的Q?/pre>
void log4cplus::thread::yield()
{
#if defined(LOG4CPLUS_USE_PTHREADS)
    ::sched_yield();
#elif defined(LOG4CPLUS_USE_WIN32_THREADS)
    ::Sleep(
0);
#endif
}
				
### 套接?###
套接字也是log4cplus中的副品,在namespace log4cplus::helpers中,实现了C/S方式的日志记录?/pre>
1. 客户端程序需要做的工作:
/* 定义一个SocketAppendercd的挂接器 */SharedAppenderPtr _append(new SocketAppender(host, 8888"ServerName"));
/* 把_append加入到logger?nbsp;*/Logger::getRoot().addAppender(_append);
/*  SocketAppendercd不需要Layout, 直接调用宏就可以信息发往loggerServer?nbsp;*/LOG4CPLUS_INFO(Logger::getRoot(), "This is a test: ")

【注?q里对宏的调用其实是调用了SocketAppender::appendQ里面有一个数据传输约定,卛_发?br>一个后l数据的总长度,然后再发送实际的数据Q?/pre>
     
    SocketBuffer buffer 
= convertToBuffer(event, serverName);
    SocketBuffer msgBuffer(LOG4CPLUS_MAX_MESSAGE_SIZE);
    msgBuffer.appendSize_t(buffer.getSize());
    msgBuffer.appendBuffer(buffer);        
				
2. 服务器端E序需要做的工作:
/* 定义一个ServerSocket */ServerSocket serverSocket(port);
 
/* 调用accept函数创徏一个新的socket与客Lq接 */Socket sock = serverSocket.accept();
				
此后卛_用该sockq行数据read/write?形如Q?/pre>
SocketBuffer msgSizeBuffer(sizeof(unsigned int));
if(!clientsock.read(msgSizeBuffer))
{
    
return;
}

unsigned 
int msgSize = msgSizeBuffer.readInt();
SocketBuffer buffer(msgSize);
if(!clientsock.read(buffer))
{
    
return;
}

Z读到的数据正常昄出来Q需要将SocketBuffer存放的内容{换成InternalLoggingEvent格式Q?/pre>
spi::InternalLoggingEvent event = readFromBuffer(buffer);
然后输出Q?br>
Logger logger = Logger::getInstance(event.getLoggerName());
logger.callAppenders(
event);
				
【注?read/write是按照阻塞方式实现的Q意味着对其调用直到满了所接收或发送的个数才返回?/pre>

]]>开源日志系llog4cplus(?http://www.shnenglu.com/tx7do/articles/11720.html杨粼?/dc:creator>杨粼?/author>Fri, 25 Aug 2006 20:50:00 GMThttp://www.shnenglu.com/tx7do/articles/11720.htmlhttp://www.shnenglu.com/tx7do/comments/11720.htmlhttp://www.shnenglu.com/tx7do/articles/11720.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/11720.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/11720.htmllog4cplus在很多方面做的都很出Ԍ但是使用q程有些地方感觉不爽。在l箋Ҏ之前我先把不爽之?br />E微提一提,然后l箋介绍关于U程和套接字的知识?br />

### 一些可以改q之?###
1. 用户自定义LogLevel的实现机制不够开?/pre>
		
在第五篇中曾l介l过如何实现用户自行定义LogLevelQؓ了实现比较理想的效果Q甚臌需要改log4cplus
的源代码。:Q?/pre>
2. 生成Logger对象的机制可以改q?/pre>
		
我在使用时候,l常需要在不同的文件、函C操作同一个loggerQ虽然log4cplus实现了树状存储以及根?br />名称生成LoggerQ却没有充分利用q样的特点确保同一个名U对应的logger对象的唯一性,比如以下代码Q?/pre>
		
    ... ...
   
    Logger logger1 = Logger::getInstance("test");
    Logger logger2 = Logger::getInstance("test");
    Logger * plogger1 = &logger1;
    Logger * plogger2 = &logger2;
    std::cout << "plogger1: " << plogger1 << std::endl << "plogger2: " << plogger2 << std::endl;
   
    ... ...
   
   
q行l果Q?/pre>
plogger1: 0xbfffe5a0
plogger2: 0xbfffe580
				
从结果可以看出,明明是同一个LoggerQ但每次调用都会产生一个Logger副本Q虽然结果是正确的(因ؓ存
储和操作分开了)Q但是资源有些浪费,我看了一下log4cplus的代码,其实可以按照如下方式实现Q示意?br />的)Q?/pre>
#include <iostream>
#include <string>
#include <map>
/* forward declaration */
class Logger;
class LoggerContainer
{
public:
    ~LoggerContainer();
    Logger * getinstance(const std::string & strLogger);
private:
    typedef std::map<:string,> LoggerMap;
    LoggerMap loggerPtrs;
};
class Logger
{
public:
     Logger() {std::cout << "ctor of Logger " << std::endl; }
    ~Logger() {std::cout << "dtor of Logger " << std::endl; }
    static Logger * getInstance( const std::string & strLogger)
    {
        static LoggerContainer defaultLoggerContainer;
        return defaultLoggerContainer.getinstance(strLogger);
    }
};
LoggerContainer::~LoggerContainer()
{
    /* release all ptr in LoggerMap */
    LoggerMap::iterator itr = loggerPtrs.begin();
    for( ; itr != loggerPtrs.end(); ++itr )
 {
     delete (*itr).second;
 }
}
Logger * LoggerContainer::getinstance(const std::string & strLogger)
{
   LoggerMap::iterator itr = loggerPtrs.find(strLogger);
   if(itr != loggerPtrs.end())
   {
       /* logger exist, just return it */
       return (*itr).second;
   }
   else
   {
       /* return a new logger */
       Logger * plogger = new Logger();
       loggerPtrs.insert(std::make_pair(strLogger, plogger));
       return plogger;
   }
}
int main()
{
    Logger * plogger1 = Logger::getInstance("test");
    Logger * plogger2 = Logger::getInstance("test");
    std::cout << "plogger1: " << plogger1 << std::endl << "plogger2: " << plogger2 << std::endl;
    return 0;
}
				
q行l果Q?/pre>
ctor of Logger
plogger1: 0x804fc30
plogger2: 0x804fc30
dtor of Logger
q里的LoggerContainer相当于log4cplus中的Hierarchyc,l果可以看出Q通过同一个名U可以获取相同的
Logger实例?/pre>
				
q有一些小毛病比如RollingFileAppender和DailyRollingFileAppender的参数输入顺序可以调整成l一方式
{等Q就不细说了?/pre>
本部分提C使用log4cplus时候感觉不爽的地方Q最后一部分介l一下log4cplus中线E和套接字实现情?br />


]]>开源日志系llog4cplus(?http://www.shnenglu.com/tx7do/articles/11719.html杨粼?/dc:creator>杨粼?/author>Fri, 25 Aug 2006 20:50:00 GMThttp://www.shnenglu.com/tx7do/articles/11719.htmlhttp://www.shnenglu.com/tx7do/comments/11719.htmlhttp://www.shnenglu.com/tx7do/articles/11719.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/11719.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/11719.html日志pȝ的另一个基本功能就是能够让使用者按照自q意愿来控制什么时候,哪些log信息可以输出?br />如果能够让用户在L时刻讄允许输出的LogLevel的信息就好了Qlog4cplus通过LogLevelManager?br />LogLog、Filter三种方式实现了上q功能?/pre>
				
### 优先U控?###
在研ILogLevelManager之前Q首先介l一下log4cplus中logger的存储机Ӟ在log4cplus中,所?br />logger都通过一个层ơ化的结构(其实内部是hash表)来组l的Q有一个RootU别的logger,可以?br />q以下方法获取:
    Logger root = Logger::getRoot();
   
用户定义的logger都有一个名字与之对应,比如Q?/pre>
    Logger test = Logger::getInstance("test");
   
可以定义该logger的子logger:
    Logger subTest = Logger::getInstance("test.subtest");
   
注意RootU别的logger只有通过getRootҎ获取QLogger::getInstance("root")获得的是它的
子对象而已。有了这些具有父子关pȝlogger之后可分别设|其LogLevel,比如Q?/pre>
root.setLogLevel( ... );
Test.setLogLevel( ... );
subTest.setLogLevel( ... );
				
logger的这U父子关联性会体现在优先控制斚wQlog4cplus输出的log信息按照LogLevel
Q从低到高)分ؓQ?/pre>
NOT_SET_LOG_LEVEL (   -1) Q接受缺省的LogLevelQ如果有父logger则承它的LogLevel
ALL_LOG_LEVEL     (    0) Q开放所有log信息输出
TRACE_LOG_LEVEL   (    0) Q开放trace信息输出(即ALL_LOG_LEVEL)
DEBUG_LOG_LEVEL   (10000) Q开放debug信息输出
INFO_LOG_LEVEL    (20000) Q开放info信息输出
WARN_LOG_LEVEL    (30000) Q开放warning信息输出
ERROR_LOG_LEVEL   (40000) Q开放error信息输出
FATAL_LOG_LEVEL   (50000) Q开放fatal信息输出
OFF_LOG_LEVEL     (60000) Q关闭所有log信息输出
LogLevelManager负责讄logger的优先Q各个logger可以通过setLogLevel讄自己的优先Q?br />当某个logger的LogLevel讄成NOT_SET_LOG_LEVELӞ该logger会承父logger的优先Q另外,
如果定义了重名的多个logger, 对其中Q何一个的修改都会同时改变其它logger,我们举例说明Q?/pre>
〖例6?/pre>
		
#include "log4cplus/logger.h"
#include "log4cplus/consoleappender.h"
#include "log4cplus/loglevel.h"
#include <iostream>
using namespace std;
using namespace log4cplus;
int main()
{
    SharedAppenderPtr _append(new ConsoleAppender());
    _append->setName("test");
    Logger::getRoot().addAppender(_append);
    Logger root = Logger::getRoot();
    Logger test = Logger::getInstance("test");
    Logger subTest = Logger::getInstance("test.subtest");
    LogLevelManager& llm = getLogLevelManager();
    cout << endl << "Before Setting, Default LogLevel" << endl;
    LOG4CPLUS_FATAL(root, "root: " << llm.toString(root.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test: " << llm.toString(test.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test.subtest: " << llm.toString(subTest.getChainedLogLevel()))
    cout << endl << "Setting test.subtest to WARN" << endl;
    subTest.setLogLevel(WARN_LOG_LEVEL);
    LOG4CPLUS_FATAL(root, "root: " << llm.toString(root.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test: " << llm.toString(test.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test.subtest: " << llm.toString(subTest.getChainedLogLevel()))
    cout << endl << "Setting test.subtest to TRACE" << endl;
    test.setLogLevel(TRACE_LOG_LEVEL);
    LOG4CPLUS_FATAL(root, "root: " << llm.toString(root.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test: " << llm.toString(test.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test.subtest: " << llm.toString(subTest.getChainedLogLevel()))
    cout << endl << "Setting test.subtest to NO_LEVEL" << endl;
    subTest.setLogLevel(NOT_SET_LOG_LEVEL);
    LOG4CPLUS_FATAL(root, "root: " << llm.toString(root.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test: " << llm.toString(test.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test.subtest: " << llm.toString(subTest.getChainedLogLevel()) << '\n')
    cout << "create a logger test_bak, named \"test_\", too. " << endl;
    Logger test_bak = Logger::getInstance("test");
    cout << "Setting test to INFO, so test_bak also be set to INFO" << endl;
    test.setLogLevel(INFO_LOG_LEVEL);
    LOG4CPLUS_FATAL(root, "test: " << llm.toString(test.getChainedLogLevel()))
    LOG4CPLUS_FATAL(root, "test_bak: " << llm.toString(test_bak.getChainedLogLevel()))
    return 0;
}
输出l果Q?/pre>
		
Before Setting, Default LogLevel
FATAL - root: DEBUG
FATAL - test: DEBUG
FATAL - test.subtest: DEBUG
Setting test.subtest to WARN
FATAL - root: DEBUG
FATAL - test: DEBUG
FATAL - test.subtest: WARN
Setting test.subtest to TRACE
FATAL - root: DEBUG
FATAL - test: TRACE
FATAL - test.subtest: WARN
Setting test.subtest to NO_LEVEL
FATAL - root: DEBUG
FATAL - test: TRACE
FATAL - test.subtest: TRACE
create a logger test_bak, named "test_", too.
Setting test to INFO, so test_bak also be set to INFO
FATAL - test: INFO
FATAL - test_bak: INFO
				
下面的例子演CZ如何通过讄LogLevel来控制用Llog信息输出Q?/pre>
〖例7?/pre>
		
#include "log4cplus/logger.h"
#include "log4cplus/consoleappender.h"
#include "log4cplus/loglevel.h"
#include <iostream>
using namespace std;
using namespace log4cplus;
void ShowMsg(void)
{
    LOG4CPLUS_TRACE(Logger::getRoot(),"info")
    LOG4CPLUS_DEBUG(Logger::getRoot(),"info")
    LOG4CPLUS_INFO(Logger::getRoot(),"info")
    LOG4CPLUS_WARN(Logger::getRoot(),"info")
    LOG4CPLUS_ERROR(Logger::getRoot(),"info")
    LOG4CPLUS_FATAL(Logger::getRoot(),"info")
}
int main()
{
    SharedAppenderPtr _append(new ConsoleAppender());
    _append->setName("test");
    _append->setLayout(std::auto_ptr(new TTCCLayout()));
    Logger root = Logger::getRoot();
    root.addAppender(_append);
    cout << endl << "all-log allowed" << endl;
    root.setLogLevel(ALL_LOG_LEVEL);
    ShowMsg();
    cout << endl << "trace-log and above allowed" << endl;
    root.setLogLevel(TRACE_LOG_LEVEL);
    ShowMsg();
    cout << endl << "debug-log and above allowed" << endl;
    root.setLogLevel(DEBUG_LOG_LEVEL);
    ShowMsg();
    cout << endl << "info-log and above allowed" << endl;
    root.setLogLevel(INFO_LOG_LEVEL);
    ShowMsg();
    cout << endl << "warn-log and above allowed" << endl;
    root.setLogLevel(WARN_LOG_LEVEL);
    ShowMsg();
    cout << endl << "error-log and above allowed" << endl;
    root.setLogLevel(ERROR_LOG_LEVEL);
    ShowMsg();
    cout << endl << "fatal-log and above allowed" << endl;
    root.setLogLevel(FATAL_LOG_LEVEL);
    ShowMsg();
    cout << endl << "log disabled" << endl;
    root.setLogLevel(OFF_LOG_LEVEL);
    ShowMsg();
    return 0;
}
输出l果Q?/pre>
		
all-log allowed
10-17-04 10:11:40,587 [1075298944] TRACE root <> - info
10-17-04 10:11:40,590 [1075298944] DEBUG root <> - info
10-17-04 10:11:40,591 [1075298944] INFO root <> - info
10-17-04 10:11:40,591 [1075298944] WARN root <> - info
10-17-04 10:11:40,592 [1075298944] ERROR root <> - info
10-17-04 10:11:40,592 [1075298944] FATAL root <> - info
trace-log and above allowed
10-17-04 10:11:40,593 [1075298944] TRACE root <> - info
10-17-04 10:11:40,593 [1075298944] DEBUG root <> - info
10-17-04 10:11:40,594 [1075298944] INFO root <> - info
10-17-04 10:11:40,594 [1075298944] WARN root <> - info
10-17-04 10:11:40,594 [1075298944] ERROR root <> - info
10-17-04 10:11:40,594 [1075298944] FATAL root <> - info
debug-log and above allowed
10-17-04 10:11:40,595 [1075298944] DEBUG root <> - info
10-17-04 10:11:40,595 [1075298944] INFO root <> - info
10-17-04 10:11:40,596 [1075298944] WARN root <> - info
10-17-04 10:11:40,596 [1075298944] ERROR root <> - info
10-17-04 10:11:40,596 [1075298944] FATAL root <> - info
info-log and above allowed
10-17-04 10:11:40,597 [1075298944] INFO root <> - info
10-17-04 10:11:40,597 [1075298944] WARN root <> - info
10-17-04 10:11:40,597 [1075298944] ERROR root <> - info
10-17-04 10:11:40,598 [1075298944] FATAL root <> - info
warn-log and above allowed
10-17-04 10:11:40,598 [1075298944] WARN root <> - info
10-17-04 10:11:40,598 [1075298944] ERROR root <> - info
10-17-04 10:11:40,599 [1075298944] FATAL root <> - info
error-log and above allowed
10-17-04 10:11:40,599 [1075298944] ERROR root <> - info
10-17-04 10:11:40,600 [1075298944] FATAL root <> - info
fatal-log and above allowed
10-17-04 10:11:40,600 [1075298944] FATAL root <> - info
log disabled
 
用户也可以自行定义LogLevelQ操作比较简单,首先要定义LEVEL|比如HELLO_LOG_LEVEL定义如下Q?/pre>
		
/* DEBUG_LOG_LEVEL  < HELLO_LOG_LEVEL < INFO_LOG_LEVEL */
const LogLevel HELLO_LOG_LEVEL = 15000;
然后定义以下宏即可:
/* define MACRO LOG4CPLUS_HELLO */
#define LOG4CPLUS_HELLO(logger, logEvent) \
    if(logger.isEnabledFor(HELLO_LOG_LEVEL)) { \
        log4cplus::tostringstream _log4cplus_buf; \
        _log4cplus_buf << logEvent; \
 logger.forcedLog(HELLO_LOG_LEVEL, _log4cplus_buf.str(), __FILE__, __LINE__); \
    }
不过log4cplus没有提供l用户一个接口来实现LEVELg字符串的转换Q所以当带格式输出LogLevel字符
串时候会昄"UNKNOWN"Q?不够理想。比如用TTCCLayout控制输出的结果可能会如下所C:
10-17-04 11:17:51,124 [1075298944] UNKNOWN root <> - info
而不是期望的以下l果Q?br />10-17-04 11:17:51,124 [1075298944] HELLO root <> - info
要想实现W二U结果,按照log4cplus现有的接口机Ӟ只能改其源代码后重新~译Q方法是在loglevel.cxx
中加入:
#define _HELLO_STRING LOG4CPLUS_TEXT("HELLO")
然后修改log4cplus::tstring  defaultLogLevelToStringMethod(LogLevel ll)函数Q增加一个判断:
case HELLO_LOG_LEVEL:    return _HELLO_STRING;
重新~译log4cplus源代码后生成库文Ӟ再用时卛_实现满意效果?/pre>
		
				
### 调试模式 ###
即通过loglog来控制输试、警告或错误信息Q见?Q这里不再赘q?/pre>
		
 
### Z脚本配置来过滤log信息 ###
除了通过E序实现对log环境的配|之外,log4cplus通过PropertyConfiguratorcdCZ脚本配置的功能?br />通过脚本可以完成对logger、appender和layout的配|,因此可以解决怎样输出Q输出到哪里的问题,我将?br />全文的最后一部分中提到多U程环境中如何利用脚本配|来配合实现性能试Q本节将重点介绍本实现过
滤log信息的功能?/pre>
首先单介l一下脚本的语法规则Q?/pre>
		
包括Appender的配|语法和logger的配|语法,其中Q?/pre>
		
1.Appender的配|语?
Q?Q设|名Uͼ
/*讄Ҏ*/
log4cplus.appender.appenderName=fully.qualified.name.of.appender.class
例如Q列举了所有可能的AppenderQ其中SocketAppender后面会讲刎ͼQ?br />log4cplus.appender.append_1=log4cplus::ConsoleAppender
log4cplus.appender.append_2=log4cplus::FileAppender
log4cplus.appender.append_3=log4cplus::RollingFileAppender
log4cplus.appender.append_4=log4cplus::DailyRollingFileAppender
log4cplus.appender.append_4=log4cplus::SocketAppender
Q?Q设|FilterQ?/pre>
		
包括选择qo器和讄qo条gQ可选择的过滤器包括QLogLevelMatchFilter、LogLevelRangeFilter?br />和StringMatchFilterQ?/pre>
		
对LogLevelMatchFilter来说Q过滤条件包括LogLevelToMatch和AcceptOnMatchQtrue|falseQ, 只有
当log信息的LogLevelgLogLevelToMatch相同Q且AcceptOnMatch为true时才会匹配?/pre>
LogLevelRangeFilter来说Q过滤条件包括LogLevelMin、LogLevelMax和AcceptOnMatchQ只有当log信息
的LogLevel在LogLevelMin、LogLevelMax之间同时AcceptOnMatch为true时才会匹配?/pre>
对StringMatchFilter来说Q过滤条件包括StringToMatch和AcceptOnMatchQ只有当log信息的LogLevel?br />与StringToMatch对应的LogLevelg相同Q?且AcceptOnMatch为true时会匚w?/pre>
		
				
qo条g处理机制cM于IPTABLE的Responsibility chainQ(卛_deny、再allowQ不q执行顺序刚好相反,
后写的条件会被先执行Q比如:
log4cplus.appender.append_1.filters.1=log4cplus::spi::LogLevelMatchFilter
log4cplus.appender.append_1.filters.1.LogLevelToMatch=TRACE
log4cplus.appender.append_1.filters.1.AcceptOnMatch=true
#log4cplus.appender.append_1.filters.2=log4cplus::spi::DenyAllFilter
会首先执行filters.2的过滤条Ӟ关闭所有过滤器Q然后执行filters.1Q仅匚wTRACE信息?/pre>
		
Q?Q设|Layout
可以选择不设|、TTCCLayout、或PatternLayout
如果不设|,会输出简单格式的log信息?/pre>
		
讄TTCCLayout如下所C:
log4cplus.appender.ALL_MSGS.layout=log4cplus::TTCCLayout
讄PatternLayout如下所C:
log4cplus.appender.append_1.layout=log4cplus::PatternLayout
log4cplus.appender.append_1.layout.ConversionPattern=%d{%m/%d/%y %H:%M:%S,%Q} [%t] %-5p - %m%n
				
2.logger的配|语?/pre>
包括rootLogger和non-root logger?/pre>
		
对于rootLogger来说Q?br />log4cplus.rootLogger=[LogLevel], appenderName, appenderName, ...
对于non-root logger来说Q?br />log4cplus.logger.logger_name=[LogLevel|INHERITED], appenderName, appenderName, ...
				
脚本方式使用h非常单,只要首先加蝲配置卛_Qurconfig.properties是自行定义的配置文gQ:
PropertyConfigurator::doConfigure("urconfig.properties");
				
下面我们通过例子体会一下log4cplus强大的基于脚本过滤log信息的功能?/pre>
				
〖例8?/pre>
/*
 *    urconfig.properties
 */
log4cplus.rootLogger=TRACE, ALL_MSGS, TRACE_MSGS, DEBUG_INFO_MSGS, FATAL_MSGS
log4cplus.appender.ALL_MSGS=log4cplus::RollingFileAppender
log4cplus.appender.ALL_MSGS.File=all_msgs.log
log4cplus.appender.ALL_MSGS.layout=log4cplus::TTCCLayout
log4cplus.appender.TRACE_MSGS=log4cplus::RollingFileAppender
log4cplus.appender.TRACE_MSGS.File=trace_msgs.log
log4cplus.appender.TRACE_MSGS.layout=log4cplus::TTCCLayout
log4cplus.appender.TRACE_MSGS.filters.1=log4cplus::spi::LogLevelMatchFilter
log4cplus.appender.TRACE_MSGS.filters.1.LogLevelToMatch=TRACE
log4cplus.appender.TRACE_MSGS.filters.1.AcceptOnMatch=true
log4cplus.appender.TRACE_MSGS.filters.2=log4cplus::spi::DenyAllFilter
log4cplus.appender.DEBUG_INFO_MSGS=log4cplus::RollingFileAppender
log4cplus.appender.DEBUG_INFO_MSGS.File=debug_info_msgs.log
log4cplus.appender.DEBUG_INFO_MSGS.layout=log4cplus::TTCCLayout
log4cplus.appender.DEBUG_INFO_MSGS.filters.1=log4cplus::spi::LogLevelRangeFilter
log4cplus.appender.DEBUG_INFO_MSGS.filters.1.LogLevelMin=DEBUG
log4cplus.appender.DEBUG_INFO_MSGS.filters.1.LogLevelMax=INFO
log4cplus.appender.DEBUG_INFO_MSGS.filters.1.AcceptOnMatch=true
log4cplus.appender.DEBUG_INFO_MSGS.filters.2=log4cplus::spi::DenyAllFilter
log4cplus.appender.FATAL_MSGS=log4cplus::RollingFileAppender
log4cplus.appender.FATAL_MSGS.File=fatal_msgs.log
log4cplus.appender.FATAL_MSGS.layout=log4cplus::TTCCLayout
log4cplus.appender.FATAL_MSGS.filters.1=log4cplus::spi::StringMatchFilter
log4cplus.appender.FATAL_MSGS.filters.1.StringToMatch=FATAL
log4cplus.appender.FATAL_MSGS.filters.1.AcceptOnMatch=true
log4cplus.appender.FATAL_MSGS.filters.2=log4cplus::spi::DenyAllFilter
				
/*
 *    main.cpp
 */
#include <log4cplus/logger.h>
#include <log4cplus/configurator.h>
#include <log4cplus/helpers/stringhelper.h>
using namespace log4cplus;
static Logger logger = Logger::getInstance("log");
void printDebug()
{
    LOG4CPLUS_TRACE_METHOD(logger, "::printDebug()");
    LOG4CPLUS_DEBUG(logger, "This is a DEBUG message");
    LOG4CPLUS_INFO(logger, "This is a INFO message");
    LOG4CPLUS_WARN(logger, "This is a WARN message");
    LOG4CPLUS_ERROR(logger, "This is a ERROR message");
    LOG4CPLUS_FATAL(logger, "This is a FATAL message");
}
int main()
{
    Logger root = Logger::getRoot();
    PropertyConfigurator::doConfigure("urconfig.properties");
    printDebug();
    return 0;
}
q行l果Q?/pre>
		
1. all_msgs.log
10-17-04 14:55:25,858 [1075298944] TRACE log <> - ENTER: ::printDebug()
10-17-04 14:55:25,871 [1075298944] DEBUG log <> - This is a DEBUG message
10-17-04 14:55:25,873 [1075298944] INFO log <> - This is a INFO message
10-17-04 14:55:25,873 [1075298944] WARN log <> - This is a WARN message
10-17-04 14:55:25,874 [1075298944] ERROR log <> - This is a ERROR message
10-17-04 14:55:25,874 [1075298944] FATAL log <> - This is a FATAL message
10-17-04 14:55:25,875 [1075298944] TRACE log <> - EXIT:  ::printDebug()
2. trace_msgs.log
10-17-04 14:55:25,858 [1075298944] TRACE log <> - ENTER: ::printDebug()
10-17-04 14:55:25,875 [1075298944] TRACE log <> - EXIT:  ::printDebug()
3. debug_info_msgs.log
10-17-04 14:55:25,871 [1075298944] DEBUG log <> - This is a DEBUG message
10-17-04 14:55:25,873 [1075298944] INFO log <> - This is a INFO message
4. fatal_msgs.log
10-17-04 14:55:25,874 [1075298944] FATAL log <> - This is a FATAL message
 
本部分详l介l了如何有选择地控制log信息的输出,最后一部分我们介l一下多U程?br />和C/S模式下该如何操作Q顺便提一下NDC的概c?/pre>


]]>开源日志系llog4cplus(?http://www.shnenglu.com/tx7do/articles/11718.html杨粼?/dc:creator>杨粼?/author>Fri, 25 Aug 2006 20:50:00 GMThttp://www.shnenglu.com/tx7do/articles/11718.htmlhttp://www.shnenglu.com/tx7do/comments/11718.htmlhttp://www.shnenglu.com/tx7do/articles/11718.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/11718.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/11718.htmllog信息记录到文件应该说是日志系l的一个基本功能,log4cplus在此基础上,提供了更多的功能Q可以按照你预先讑֮的大来军_是否转储Q当过该大,后箋log信息会另存到新文件中Q依ơ类推;或者按照日期来军_是否转储。本文将详细介绍q些用法?/p>
				
### 如何log记录到文?###
我们在例5中给Z一个将log记录到文件的例子Q用的是FileAppendercd现的Qlog4cplus提供了三个类用于
文g操作Q它们是FileAppendercRRollingFileAppendercRDailyRollingFileAppendercR?/pre>
1. FileAppenderc?/pre>
		
实现了基本的文g操作功能Q构造函数如下:
FileAppender(const log4cplus::tstring& filename,
                     LOG4CPLUS_OPEN_MODE_TYPE mode = LOG4CPLUS_FSTREAM_NAMESPACE::ios::trunc,
                     bool immediateFlush = true);
                    
filename       : 文g?br />mode           : 文gcdQ可选择的文件类型包括app、ate、binary、in、out、truncQ因为实际上只是?br />                 stl的一个简单包装,呵呵Q这里就不多讲了。缺省是truncQ表C将先前文g删除?br />immediateFlush Q缓冲刷新标志,如果为true表示每向文g写一条记录就h一ơ缓存,否则直到FileAppender
                 被关闭或文g~存已满才更新文Ӟ一般是要设|true的,比如你往文g写的q程中出?br />                 了错误(如程序非正常退出)Q即使文件没有正常关闭也可以保证E序l止时刻之前的所?br />                 记录都会被正怿存?/pre>
FileAppendercȝ使用情况请参考例5Q这里不再赘q?/pre>
		
				
2. RollingFileAppenderc?/pre>
构造函数如下:
log4cplus::RollingFileAppender::RollingFileAppender(const log4cplus::tstring& filename,
                                                    long maxFileSize,
                                                    int maxBackupIndex,
                                                    bool immediateFlush)
filename       : 文g?br />maxFileSize    : 文g的最大尺?br />maxBackupIndex : 最大记录文件数
immediateFlush : ~冲h标志
                                                   
RollingFileAppendercd以根据你预先讑֮的大来军_是否转储Q当过该大,后箋log信息会另存到?br />文g中,除了定义每个记录文g的大之外,你还要确定在RollingFileAppendercd象构造时最多需要多个
q样的记录文?maxBackupIndex+1)Q当存储的文件数目超qmaxBackupIndex+1Ӟ会删除最早生成的文gQ?br />保证整个文g数目{于maxBackupIndex+1。然后l记录,比如以下代码片段Q?/pre>
    ... ...
   
    #define LOOP_COUNT 200000
   
    SharedAppenderPtr _append(new RollingFileAppender("Test.log", 5*1024, 5));
    _append->setName("file test");
    _append->setLayout( std::auto_ptr(new TTCCLayout()) );
    Logger::getRoot().addAppender(_append);
    Logger root = Logger::getRoot();
    Logger test = Logger::getInstance("test");
    Logger subTest = Logger::getInstance("test.subtest");
    for(int i=0; i    {
        NDCContextCreator _context("loop");
        LOG4CPLUS_DEBUG(subTest, "Entering loop #" << i)
    }
   
    ... ...
   
q行l果Q?/pre>
		
q行后会产生6个输出文ӞTest.log、Test.log.1、Test.log.2、Test.log.3、Test.log.4、Test.log.5
其中Test.log存放着最新写入的信息Q而最后一个文件中q不包含W一个写入信息,说明已经被不断更C?br />需要指出的是,q里除了Test.log之外Q每个文件的大小都是200K,而不是我们想像中?KQ这是因?br />log4cplus中隐含定义了文g的最尺寸是200KQ只有大?00K的设|才生效Q?lt;= 200k的设|都会被认ؓ?br />200K.
				
3. DailyRollingFileAppenderc?/pre>
构造函数如下:
DailyRollingFileAppender::DailyRollingFileAppender(const log4cplus::tstring& filename,
                                                   DailyRollingFileSchedule schedule,
                                                   bool immediateFlush,
                                                   int maxBackupIndex)
                                                  
filename       : 文g?br />schedule       : 存储频度
immediateFlush : ~冲h标志
maxBackupIndex : 最大记录文件数
DailyRollingFileAppendercd以根据你预先讑֮的频度来军_是否转储Q当过该频度,后箋log信息会另?br />到新文g中,q里的频度包括:MONTHLYQ每月)、WEEKLYQ每周)、DAILYQ每日)、TWICE_DAILYQ每两天Q?br />HOURLYQ每Ӟ、MINUTELYQ每分)。maxBackupIndex的含义同上所qͼ比如以下代码片段Q?/pre>
		
    ... ...
   
    SharedAppenderPtr _append(new DailyRollingFileAppender("Test.log", MINUTELY, true, 5));
    _append->setName("file test");
    _append->setLayout( std::auto_ptr(new TTCCLayout()) );
    Logger::getRoot().addAppender(_append);
    Logger root = Logger::getRoot();
    Logger test = Logger::getInstance("test");
    Logger subTest = Logger::getInstance("test.subtest");
    for(int i=0; i    {
        NDCContextCreator _context("loop");
        LOG4CPLUS_DEBUG(subTest, "Entering loop #" << i)
    }
   
    ... ...
				
q行l果Q?/pre>
q行后会以分钟ؓ单位Q分别生成名为Test.log.2004-10-17-03-03、Test.log.2004-10-17-03-04?br />Test.log.2004-10-17-03-05q样的文件?/pre>
		
需要指出的是,刚看到按照频度(如HOURLY、MINUTELYQ{储这L概念Q以为log4cplus提供了内部定时器Q?br />感觉很奇怪,因ؓ日志pȝ不应该主动记录,而loging事gL应该被动触发的啊。仔l看了源代码后才知道
q里?频度"q不是你写入文g的速度Q其实是否{储的标准q不依赖你写入文件的速度Q而是依赖于写?br />的那一时刻是否满了频度条Ӟx否超q了以分钟、小时、周、月为单位的旉dQ如果超q了另存?/pre>
本部分详l介llog信息的几U文件操作方式,下面重点介l一下如何有选择地控制log信息的输出?/pre>


]]>开源日志系llog4cplus(?http://www.shnenglu.com/tx7do/articles/11717.html杨粼?/dc:creator>杨粼?/author>Fri, 25 Aug 2006 20:49:00 GMThttp://www.shnenglu.com/tx7do/articles/11717.htmlhttp://www.shnenglu.com/tx7do/comments/11717.htmlhttp://www.shnenglu.com/tx7do/articles/11717.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/11717.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/11717.html本文介绍了三U控制输出格式的布局理器的概念和用情况,通过掌握q些知识Q可以更有效地控制logpȝ输出可能脓q你需求的信息来?br />

				
### 如何控制输出消息的格?###
前面已经讲过Qlog4cplus通过布局器(LayoutsQ来控制输出的格式,log4cplus提供了三U类型的LayoutsQ?br />分别是SimpleLayout、PatternLayout、和TTCCLayout。其中:
1. SimpleLayout
是一U简单格式的布局器,在输出的原始信息之前加上LogLevel和一?-"?/pre>
比如以下代码片段Q?/pre>
		
    ... ...
    /* step 1: Instantiate an appender object */
    SharedObjectPtr _append (new ConsoleAppender());
    _append->setName("append for test");
    /* step 2: Instantiate a layout object */
    std::auto_ptr  _layout(new log4cplus::SimpleLayout());
    /* step 3: Attach the layout object to the appender */
    _append->setLayout( _layout );
    /* step 4: Instantiate a logger object */
    Logger _logger = Logger::getInstance("test");
    /* step 5: Attach the appender object to the logger  */
    _logger.addAppender(_append);
     /* log activity */
    LOG4CPLUS_DEBUG(_logger, "This is the simple formatted log message...")
   
    ... ...
   
   
打印结果:
DEBUG - This is the simple formatted log message...
2. PatternLayout
是一U有词法分析功能的模式布局器,一提v模式׃惌v正则表达式,q里的模式和正则表达式类|但是
q比后者简单,能够寚w定义的标识符Q称为conversion specifiersQ进行解析,转换成特定格式输出。以?br />代码片段演示了如何用PatternLayoutQ?/pre>
    ... ...
    /* step 1: Instantiate an appender object */
    SharedObjectPtr _append (new ConsoleAppender());
    _append->setName("append for test");
  
    /* step 2: Instantiate a layout object */
    std::string pattern = "%d{%m/%d/%y %H:%M:%S}  - %m [%l]%n";
    std::auto_ptr _layout(new PatternLayout(pattern));
   
    /* step 3: Attach the layout object to the appender */
    _append->setLayout( _layout );
    /* step 4: Instantiate a logger object */
    Logger _logger = Logger::getInstance("test_logger.subtest");
    /* step 5: Attach the appender object to the logger  */
    _logger.addAppender(_append);
     /* log activity */
    LOG4CPLUS_DEBUG(_logger, "teststr")
   
    ... ...
   
输出l果Q?br />10/16/04 18:51:25  - teststr [main.cpp:51]
可以看出通过填写特定格式的模式字W串"pattern"Q原始信息被包含C堆有格式的信息当中了Q这׃?br />用户可以Ҏ自n需要来定制昄内容?pattern"可以包含普通字W串和预定义的标识符Q其中:
Q?Q普通字W串Q能够被直接昄的信息?br />Q?Q预定义标识W,通过"%"与一个或多个字符共同构成预定义的标识W,能够产生出特定格式信息?/pre>
		
关于预定义标识符Qlog4cplus文档中提供了详细的格式说明,我每U都试了一下,以上qC码ؓ例,Ҏ不同
的patternQ各U消息格式用情况列丑֦下:
Q?Q?%%"Q{义ؓ%, 卻Istd::string pattern = "%%" 时输? "%"
Q?Q?%c"Q输出logger名称Q比如std::string pattern ="%c" 时输? "test_logger.subtest"Q?br />     也可以控制logger名称的显C层ơ,比如"%c{1}"时输?test_logger"Q其中数字表C层ơ?br />Q?Q?%D"Q显C本地时_当std::string pattern ="%D" 时输?"2004-10-16 18:55:45"Q?d昄标准旉Q?br />     所以当std::string pattern ="%d" 时输?"2004-10-16 10:55:45" Q因为我们是?区,?个小时啊Q?br />     可以通过%d{...}定义更详l的昄格式Q比?d{%H:%M:%s}表示要显C小?分钟Q秒。大括号中可昄?br />     预定义标识符如下Q?br />    
%a -- 表示C拜几,英文~写形式Q比?Fri"
%A -- 表示C拜几,比如"Friday"
%b -- 表示几月份,英文~写形式Q比?Oct"
%B -- 表示几月份,"October"
%c -- 标准的日期+旉格式Q如 "Sat Oct 16 18:56:19 2004"
%d -- 表示今天是这个月的几?1-31)"16"
%H -- 表示当前时刻是几?0-23)Q如 "18"
%I -- 表示当前时刻是几?1-12)Q如 "6"
%j -- 表示今天是哪一?1-366)Q如 "290"
%m -- 表示本月是哪一?1-12)Q如 "10"
%M -- 表示当前时刻是哪一分钟(0-59)Q如 "59"
%p -- 表示现在是上午还是下午, AM or PM
%q -- 表示当前时刻中毫U部?0-999)Q如 "237"
%Q -- 表示当前时刻中带数的毫U部?0-999.999)Q如 "430.732"
%S -- 表示当前时刻的多秒(0-59)Q如 "32"
%U -- 表示本周是今q的W几个礼拜,以周日ؓW一天开始计?0-53)Q如 "41"
%w -- 表示C拜几,(0-6, C拜天ؓ0)Q如 "6"
%W -- 表示本周是今q的W几个礼拜,以周一为第一天开始计?0-53)Q如 "41"
%x -- 标准的日期格式,?"10/16/04"
%X -- 标准的时间格式,?"19:02:34"
%y -- 两位数的q䆾(0-99)Q如 "04"
%Y -- 四位数的q䆾Q如 "2004"
%Z -- 时区名,比如 "GMT"
Q?Q?%F"Q输出当前记录器所在的文g名称Q比如std::string pattern ="%F" 时输? "main.cpp"
Q?Q?%L"Q输出当前记录器所在的文g行号Q比如std::string pattern ="%L" 时输? "51"
Q?Q?%l"Q输出当前记录器所在的文g名称和行P比如std::string pattern ="%L" 时输?
     "main.cpp:51"
Q?Q?%m"Q输出原始信息,比如std::string pattern ="%m" 时输? "teststr"Q即上述代码?br />     LOG4CPLUS_DEBUG的第二个参数Q这U实现机制可以确保原始信息被嵌入到带格式的信息中?br />Q?Q?%n"Q换行符Q没什么好解释?br />Q?Q?%p"Q输出LogLevelQ比如std::string pattern ="%p" 时输? "DEBUG"
Q?0Q?%t"Q输录器所在的U程IDQ比如std::string pattern ="%t" 时输? "1075298944"
Q?1Q?%x"Q嵌套诊断上下文NDC (nested diagnostic context) 输出Q从堆栈中弹Z下文信息QNDC可以用对
      不同源的log信息Q同时地Q交叉输行区分,关于NDC斚w的详l介l会在下文中提到?br />Q?2Q格式对齐,比如std::string pattern ="%-10m"时表C左寚wQ宽度是10Q此时会输出"teststr   "Q当
      然其它的控制字符也可以相同的方式来用,比如"%-12d"Q?%-5p"{等Q刚接触log4cplus文档时还以ؓ
      "%-5p"整个字符串代表LogLevel呢,呵呵Q?/pre>
      
3. TTCCLayout
是在PatternLayout基础上发展的一U缺省的带格式输出的布局器, 其格式由旉Q线EIDQLogger和NDC l?br />成(consists of time, thread, Logger and nested diagnostic context information, hence the nameQ,
因而得名(怎么得名的?Logger里哪里有那个"C"的羃写啊Q名字v得真够烂的,x人)。提供给那些xC?br />典型的信息(一般情况下够用了)又懒得配|pattern的同志们?/pre>
TTCCLayout在构造时有机会选择昄本地旉或GMT旉Q缺省是按照本地旉昄Q?br />TTCCLayout::TTCCLayout(bool use_gmtime  = false)
以下代码片段演示了如何用TTCCLayoutQ?/pre>
		
    ... ...
    /* step 1: Instantiate an appender object */
    SharedObjectPtr _append (new ConsoleAppender());
    _append->setName("append for test");
    /* step 2: Instantiate a layout object */
    std::auto_ptr _layout(new TTCCLayout());
    /* step 3: Attach the layout object to the appender */
    _append->setLayout( _layout );
    /* step 4: Instantiate a logger object */
    Logger _logger = Logger::getInstance("test_logger");
    /* step 5: Attach the appender object to the logger  */
    _logger.addAppender(_append);
     /* log activity */
    LOG4CPLUS_DEBUG(_logger, "teststr")
   
    ... ...
   
输出l果Q?br />10-16-04 19:08:27,501 [1075298944] DEBUG test_logger <> - teststr
				
当构造TTCCLayout对象旉择GMT旉格式Ӟ
    ... ...
   
    /* step 2: Instantiate a layout object */
    std::auto_ptr _layout(new TTCCLayout(true));
   
    ... ...
   
输出l果Q?br />10-16-04 11:12:47,678 [1075298944] DEBUG test_logger <> - teststr
				
本文介绍了控制log信息格式的相关知识,下一部分详l介llog信息的几U文件操作方式?/pre>

]]>开源日志系llog4cplus(?http://www.shnenglu.com/tx7do/articles/11716.html杨粼?/dc:creator>杨粼?/author>Fri, 25 Aug 2006 20:49:00 GMThttp://www.shnenglu.com/tx7do/articles/11716.htmlhttp://www.shnenglu.com/tx7do/comments/11716.htmlhttp://www.shnenglu.com/tx7do/articles/11716.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/11716.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/11716.html阅读全文

]]>
开源日志系llog4cplus(一)http://www.shnenglu.com/tx7do/articles/11715.html杨粼?/dc:creator>杨粼?/author>Fri, 25 Aug 2006 20:45:00 GMThttp://www.shnenglu.com/tx7do/articles/11715.htmlhttp://www.shnenglu.com/tx7do/comments/11715.htmlhttp://www.shnenglu.com/tx7do/articles/11715.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/11715.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/11715.htmllog4cplus是C++~写的开源的日志pȝQ功能非常全面,用到自己开发的工程中会比较专业的,Q)Q本文介l了log4cplus基本概念Q以及如何安装,配置?

				
### ?###
log4cplus是C++~写的开源的日志pȝQ前w是java~写的log4jpȝ.受Apache Software License
保护。作者是Tad E. Smith。log4cplushU程安全、灵zR以及多_度控制的特点,通过信息划?br>优先U其可以面向程序调试、运行、测试、和l护{全生命周期Q?你可以选择信息输出到屏幕、文件?br>NT event log、甚xq程服务器;通过指定{略Ҏ志进行定期备份等{?/pre>
 
### 下蝲 ###
最新的log4cplus可以从以下网址下蝲 http://log4cplus.sourceforge.net
本文使用的版本ؓQ?.0.2
 
### 安装 ###
 
1. linux下安?/pre>
tar xvzf log4cplus-x.x.x.tar.gz
cd log4cplus
-x.x.x.
/configure --prefix=/where/to/install
make
make install

q里我采用缺省安装\径:/usr/localQ下文如无特别说明,均以此\径ؓ准?/pre>
 
2. windows下安?/pre>
不需要安装,有一个msvc6存放包括源代码和用例在内的开发工E(for VC6 onlyQ,使用之前请先~译
"log4cplus_dll class"工程生成dllQ或者编?log4cplus_static class"工程生成lib.
 
### 使用前的配置 ###
1. linux下的配置
保你的Makefile中包?/usr/local/lib/liblog4cplus.aQ静态库Q或  -llog4cplusQ动态库Q即可,
头文件在/usr/local/include/log4cplus目录下。对于动态库Q要x怋用,q得库安装路径加入?br>LD_LIBRARY_PATH 中,我一般是q样做的Q以理员n份登录,?etc/ld.so.conf中加入安装\径,q里
?usr/local/libQ然后执行ldconfig使设|生效即可?/pre>
2. windows下的配置
?log4cplus_dll class"工程?log4cplus_static class"工程的dsp 文g插入C的工E中Q或者直?br>把两个工E编译生成的库以及头文g所在目录放C的工E的搜烦路径中,如果你用静态库Q请在你的工E中
"project/setting/C++"的preprocessor definitions中加入LOG4CPLUS_STATIC?/pre>
 
### 构成要素介绍 ###
虽然功能强大Q应该说log4cplus用v来还是比较复杂的Qؓ了更好地使用它,先介l一下它的基本要素?/pre>
Layouts      Q布局器,控制输出消息的格?
Appenders    Q挂接器Q与布局器紧密配合,特定格式的消息输出到所挂接的设备终?br>               Q如屏幕Q文件等{??br>Logger       Q记录器Q保存ƈ跟踪对象日志信息变更的实体,当你需要对一个对象进?br>               记录Ӟ需要生成一个logger?br>Categories   Q分cdQ层ơ化QhierarchyQ的l构Q用于对被记录信息的分类Q层ơ中
               每一个节点维护一个logger的所有信息?br>Priorities   Q优先权Q包括TRACE, DEBUG, INFO, WARNING, ERROR, FATAL?/pre>
				
本文介绍了log4cplus基本概念Q以及如何安装,配置Q下一将通过例子介绍如何使用log4cplus?/pre>

]]>VC中加入定时机制的几种Ҏhttp://www.shnenglu.com/tx7do/articles/8923.html杨粼?/dc:creator>杨粼?/author>Fri, 23 Jun 2006 13:48:00 GMThttp://www.shnenglu.com/tx7do/articles/8923.htmlhttp://www.shnenglu.com/tx7do/comments/8923.htmlhttp://www.shnenglu.com/tx7do/articles/8923.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/8923.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/8923.html 定时机制是指在程序运行当中间隔特定的旉引发指定的事件。在DOS下编E时Q主要依靠时钟中断Int 8及其调用中断 Int 1cH来实玎ͼ应用E序通过修改q些pȝ中断来达到实?font style="BACKGROUND-COLOR: yellow" color="red">定时触发。而在Windows下,若想象在DOS下肆无忌惮的修改pȝ是不现实的,那么应当如何实现定时机制呢?下面在下在学习当中的几点体会谈谈这个问题,提出几种Ҏ供大家参考?/p>

W一U方案是大家熟悉的截?font style="BACKGROUND-COLOR: yellow" color="red">定时消息的途径。在Windows提供l我们用的pȝ资源当中Q有一U称为?font style="BACKGROUND-COLOR: yellow" color="red">定时器(TimerQ”的Ҏ资源Q在甌了这c资源的E序当中每间隔一D|间会接收到gؓWM_TIMER的消息。需?font style="BACKGROUND-COLOR: yellow" color="red">定时执行的代码可以放在该消息的处理部分。如果在VC中,我们可以具体按照以下步骤实现q一目的Q?/p>

  1. 利用MFC AppWizard创徏一个标准的工程Q接受所有缺省选项。名为s1

  2. 在Classview中选中“CMainFrame”类Q然后按Ctrl+WȀzClassWizardQ在“Message Map”选项卡中Class Name选“CMainFrame”,接着在“Message”中选“WM_TIMER”,最后按下“Add Funcation”。以上步骤加入了对WM_TIMER消息的映处理?

  3. 回到Classview中,双击“OnCreate”成员函敎ͼ在函数的末尾d甌Timer的语句:
    SetTimer(100,1000,NULL);//甌一个标识gؓ100的TimerQ?font style="BACKGROUND-COLOR: yellow" color="red">定时间隔?000毫秒Q?U)?

  4. 在“Classview”中双击OnTimer函数Q输入要定时实现的代码。本例子中ؓQ?br />MessageBeep(1000);;//每隔一U发出通告?

  5. ~译q执行之Q我们可以每隔一U就听到声音。这正是我们在OnTimer函数内要求执行的?

实际当中Q我们可以将“MessageBeep(1000);”换成Q何我们想完成的Q务,譬如定时存盘{?/p>

W二U方案也利用Timer资源Q但却是采用已经~写好的代码&#0;&#0;我们可以加入一个具?font style="BACKGROUND-COLOR: yellow" color="red">定时功能的组件至当前工程当中。这U方法特别适用于基于对话框的工E。具体步骤如下:

  1. 利用MFC AppWizard创徏一个基于对话框的工E,其余接受所有缺省选项。名为s2?

  2. 在ResourceView中,双击IDD_S2_DIALOGQ显C对话框Q将其中的“To do:”改为?font style="BACKGROUND-COLOR: yellow" color="red">定时触发演示的例子”,表明工程的作用?

  3. 叛_对话框编辑区Q在弹出的右键菜单中选择“Insert ActiveX Control”,从弹出的列表框中选择“Timer Object”,定后会在对话框内出C个Timer对象?

  4. 我们叛_Timer对象Q从弹出的菜单中选择“Properties”,接着选“All”选项卡,其中的IntervalD?000Q即每隔5U发生一ơTimer事g?

  5. 回到对话框编辑界面,双击TimerQ生一个CS2Dlg::OnTimerTimer1成员函数Q接受缺省|q在函数实现部分输入Q?br />MessageBox("定时触发消息?,"定时演示" ,MB_OK);

  6. ~译q运行此工程Q将会在产生的对话框q行期间Q每?U弹Z个消息框?

同样Q我们可以以M自己的代码来替换5中的消息框语句。详l见附例s2?/p>

W三U方法是采用U程技术。众所周知QWindows 9X是一个基于多U程的多d操作pȝQ在内核中以U程作ؓ调度的基本单位,ql分旉片进行调度。利用这一点,我们可以在程序当中创Z个“司职”计时的U程Q通过U程间的同步?font style="BACKGROUND-COLOR: yellow" color="red">定时触发我们要完成的d的代码。不象前两种Ҏ需要至有一个窗口作为接受消息的ȝ口,采用U程技术实?font style="BACKGROUND-COLOR: yellow" color="red">定时触发免d建窗口的ȝ以及带来的系l各U资源的消耗。下面我们来举一个例子来说明q个问题Q我们在CmyAppcȝInitstance成员中不建立ȝ口而是创徏一个工作线E,该线E休眠一定的旉后,自动调用ȝE的SomeThing函数。ؓ了支持线E的q行Q我们需要给CmyAppcd加相应的U程函数。下面,我们q是一步一步的实现Q?/p>

  1. 利用MFC AppWizard创徏一个标准工E,其中Z产生多余的代码,不选文?视图支持Qƈ选择单文档。工E名为S3?

  2. 在CS3App:: InitInstance()中用?* ?*/”注释掉“return TRUE;”之前的所有代码。这是ؓ了不建立H口。ƈd以下代码Q?br />ExitFlag=TRUE;//是否l束ȝE的循环的标志变量。因为子U程严重依赖ȝE,所以在本例子中Z避免没有ȝ口而提前结束应用程序,从而子线E无法存在,所以给ȝE一个@环,知道全局变量ExitFlag在子U程退出前被设|成FALSE为止.
    StartThread();//启动U程
    do{}while(ExitFlag);//直到l束子线E?br />::MessageBox(NULL,"ȝE结束!","定时触发演示",MB_OK);
    return TRUE;

  3. 在Globals中增加一标志变量“ExitFlag”,cd为BOOL。它被主U程用来判断是否l束自nq行?

  4. 通过ClassView在CS3App的Public部分声明以下函数:
    void StartThread(void); //启动U程
    static UINT ThreadFunction(void); //主要执行代码的函?br />static UINT StaticThreadFunc(LPVOID lpparam);//讄U程时用到的函数
    需要特别指出的是,用AfxBeginThreadq行U程讄ӞW一参数必须象本例所指出的那样声明ؓStatic Q不然参数{换的错误会扰得你不得安宁?

  5. 在StartThread中输入如下代码:
    AfxBeginThread(StaticThreadFunc,this);//建立q启动线E?

  6. 在StaticThreadFunc中输入如下代码:
    return ThreadFunc();//调用完成主要U程代码的函敎ͼ注意一定要是Static.

  7. 实现ThreadFunctionQ?br />int i;
    i=5;//触发5?br />while(i--)
    {
    Sleep(5000);//间隔5U?br />::MessageBox (NULL,"我被定时触发了!","定时触发演示",MB_OK);
    }
    ExitFlag=FALSE;//ExitFlag是一全局变量Q通知ȝE结束运行?br />return 0;
    }

  8. ~译q运行工E,看不到应用E序H口Q但可以看到每隔5U,桌面上出C个消息框Q?ơ后弹出ȝE结束的消息框?

以上x人在学习当中解决 Windows下实?font style="BACKGROUND-COLOR: yellow" color="red">定时触发而采取的一些办法,各自Ҏ的特点也在介l当中指出。希望所q能l大家一点帮助,更希望能得到大家的指正。如果您有什么意见和设想Q欢q发E-Maill我Q?a href="mailto:yangshanhe@21cn.com">yangshanhe@21cn.comQ?/p>

 

==

很早之前2000q的拙作Q集在一P免得自己都不清楚q过什么?/p>

]]>
INF文g格式说明http://www.shnenglu.com/tx7do/articles/8922.html杨粼?/dc:creator>杨粼?/author>Fri, 23 Jun 2006 13:48:00 GMThttp://www.shnenglu.com/tx7do/articles/8922.htmlhttp://www.shnenglu.com/tx7do/comments/8922.htmlhttp://www.shnenglu.com/tx7do/articles/8922.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/8922.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/8922.html阅读全文

]]>
如何对webbrowser和IE~程Q十一Q?/title><link>http://www.shnenglu.com/tx7do/articles/8921.html</link><dc:creator>杨粼?/dc:creator><author>杨粼?/author><pubDate>Fri, 23 Jun 2006 13:46:00 GMT</pubDate><guid>http://www.shnenglu.com/tx7do/articles/8921.html</guid><wfw:comment>http://www.shnenglu.com/tx7do/comments/8921.html</wfw:comment><comments>http://www.shnenglu.com/tx7do/articles/8921.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.shnenglu.com/tx7do/comments/commentRss/8921.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/tx7do/services/trackbacks/8921.html</trackback:ping><description><![CDATA[     摘要: 仅仅用于Internet Explorer的事? 有些是仅仅可用于自动?Internet Explorer,: ·         OnQuit ...  <a href='http://www.shnenglu.com/tx7do/articles/8921.html'>阅读全文</a><img src ="http://www.shnenglu.com/tx7do/aggbug/8921.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/tx7do/" target="_blank">杨粼?/a> 2006-06-23 21:46 <a href="http://www.shnenglu.com/tx7do/articles/8921.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>如何对webbrowser和IE~程Q十Q?/title><link>http://www.shnenglu.com/tx7do/articles/8920.html</link><dc:creator>杨粼?/dc:creator><author>杨粼?/author><pubDate>Fri, 23 Jun 2006 13:46:00 GMT</pubDate><guid>http://www.shnenglu.com/tx7do/articles/8920.html</guid><wfw:comment>http://www.shnenglu.com/tx7do/comments/8920.html</wfw:comment><comments>http://www.shnenglu.com/tx7do/articles/8920.html#Feedback</comments><slash:comments>2</slash:comments><wfw:commentRss>http://www.shnenglu.com/tx7do/comments/commentRss/8920.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/tx7do/services/trackbacks/8920.html</trackback:ping><description><![CDATA[     摘要: 由Internet Explorer 5Ȁ发事? 如你所知, Internet Explorer像其他COM对象一h发事件—通过q接?但实际上Internet Explorer如何Ȁ发事件呢?每次 Internet Explorer需要向客户提供关于当前zd状态的信息, Internet Explorer Ȁ发通过DWebBrowserEvents2 ...  <a href='http://www.shnenglu.com/tx7do/articles/8920.html'>阅读全文</a><img src ="http://www.shnenglu.com/tx7do/aggbug/8920.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/tx7do/" target="_blank">杨粼?/a> 2006-06-23 21:46 <a href="http://www.shnenglu.com/tx7do/articles/8920.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>如何对webbrowser和IE~程Q九Q?http://www.shnenglu.com/tx7do/articles/8919.html杨粼?/dc:creator>杨粼?/author>Fri, 23 Jun 2006 13:45:00 GMThttp://www.shnenglu.com/tx7do/articles/8919.htmlhttp://www.shnenglu.com/tx7do/comments/8919.htmlhttp://www.shnenglu.com/tx7do/articles/8919.html#Feedback1http://www.shnenglu.com/tx7do/comments/commentRss/8919.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/8919.html阅读全文

]]>
如何对webbrowser和IE~程Q八Q?/title><link>http://www.shnenglu.com/tx7do/articles/8918.html</link><dc:creator>杨粼?/dc:creator><author>杨粼?/author><pubDate>Fri, 23 Jun 2006 13:44:00 GMT</pubDate><guid>http://www.shnenglu.com/tx7do/articles/8918.html</guid><wfw:comment>http://www.shnenglu.com/tx7do/comments/8918.html</wfw:comment><comments>http://www.shnenglu.com/tx7do/articles/8918.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.shnenglu.com/tx7do/comments/commentRss/8918.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/tx7do/services/trackbacks/8918.html</trackback:ping><description><![CDATA[ <h1 style="MARGIN: auto 0cm"> <span lang="EN-US"> <font face="宋体">Internet Explorer 事g</font> </span> </h1> <p> <span lang="EN-US"> <font face="宋体"> <font size="3"> <p> </p> </font> </font> </span> </p> <p> </p> <p> <font face="宋体"> <font size="3"> <i> <span lang="EN-US">IWebBrowser2 </span> </i>的属性和Ҏl了你确切的控制D和用h口的途径Q但是如果你不能够检到览器正在处理什么以及何时处理什么,你还是没有全面的控制?span lang="EN-US">.因此QWebBrowser控g和Internet Explorer暴露ZӞ通过此你可以必要时监视活动以及处理某些活? 举例来说Q假设你建立一个intranet应用E序, 你想限制用户用户讉K某些web?利用Internet Explorer的时间处理句?你可以指令应用程序在用户试图讉K受限的URL时候取消导航完成?/span></font> </font> </p> <p> <span lang="EN-US"> <font face="宋体"> <font size="3"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <h1 style="MARGIN: auto 0cm"> <font face="宋体">事g ?引出的接?/font> </h1> <p> <font size="3"> <font face="宋体">无论何时一?span lang="EN-US">COM 对象需要客户应用程序一个事件发生了, COM 对象发送一个叫做事件的消息. 发送消息的处理q程会激发一个事? 但如果事件没有Q何监听者会如何Q?事g每次都发生吗? 昄, 客户应用E序监听q些事gq控制COM对象.如果一个客户应用想接收来自COM 对象的事??advises" 实际的COM 对象?</span></font> </font> </p> <p> <font size="3"> <font face="宋体">一?span lang="EN-US">COM 对象Z通客户通信, 对象自n必须支持一个或者多个外引接?一?COM 对象支持的外引接口是作ؓ可连接对象引? 要成Z个可q接对象QCOM对象必须实现<i>IConnectionPointContainer </i>接口。通过此接口,客户可认识到那些外引接口被服务器支持. 外引接口实际通过q接点由客户挂接入COM实现。实现外引接口的客户部分众所周知是通过事g接收槽(event sinkQ实现的.</span></font> </font> </p> <p> <font size="3"> <font face="宋体">单一的连接点由服务器支持每一个外引接?span lang="EN-US">.每一个连接点能够操纵一U类型的外引接口且至支?i>IConnectionPoint</i> 接口. ?-1 描述了可q接的对象和它的客户之间的关p?</span></font> </font> </p> <p> <span lang="EN-US"> <font size="3"> <font face="宋体"> <shapetype id="_x0000_t75" stroked="f" filled="f" path="m@4@5l@4@11@9@11@9@5xe" o:preferrelative="t" o:spt="75" coordsize="21600,21600"> <stroke joinstyle="miter"> </stroke> <formulas> <f eqn="if lineDrawn pixelLineWidth 0"> </f> <f eqn="sum @0 1 0"> </f> <f eqn="sum 0 0 @1"> </f> <f eqn="prod @2 1 2"> </f> <f eqn="prod @3 21600 pixelWidth"> </f> <f eqn="prod @3 21600 pixelHeight"> </f> <f eqn="sum @0 0 1"> </f> <f eqn="prod @6 1 2"> </f> <f eqn="prod @7 21600 pixelWidth"> </f> <f eqn="sum @8 21600 0"> </f> <f eqn="prod @7 21600 pixelHeight"> </f> <f eqn="sum @10 21600 0"> </f> </formulas> <path o:connecttype="rect" gradientshapeok="t" o:extrusionok="f"> </path> <lock aspectratio="t" v:ext="edit"> </lock> </shapetype> <shape id="_x0000_i1025" style="WIDTH: 297pt; HEIGHT: 143.25pt" type="#_x0000_t75"> <imagedata o:title="CH7-1_Events" src="file:///C:/DOCUME~1/ADMINI~1/LOCALS~1/Temp/msoclip1/01/clip_image001.jpg"> </imagedata> </shape> </font> </font> </span> </p> <p> <font size="3"> <font face="宋体"> <b> <span lang="EN-US">Figure 7-1.</span> </b> <span lang="EN-US"> <i>Connectable object and its client.</i> </span> </font> </font> </p> <p> <font size="3"> <font face="宋体">每一个服务器必须实现<span lang="EN-US">2个接口以便实现客户可以接收事件?i>IConnectionPointContainer</i> ?<i>IConnectionPoint</i>. 我们先看看q些接口之后检视实C件的不同途径.</span></font> </font> </p> <h2 style="MARGIN: auto 0cm"> <i> <span lang="EN-US"> <font face="宋体">IConnectionPointContainer</font> </span> </i> </h2> <p> <font face="宋体"> <font size="3">每一个可q接对象实现?i><span lang="EN-US">IConnectionPointContainer</span></i><span lang="EN-US">. 通过此接? 试图接收事g的客户可扑և关于可连接对象支持的不同的连接点. 通过调用<i>QueryInterface </i>using 客户可以获得服务器支持的M接口的指? (你可以用Q何接口指针调?i>QueryInterface</i>, 因ؓ全部 COM 接口l承?i>IUnknown</i>.) 之后客户可以使用<i>IConnectionPointContainer</i> 接口?个方法中的之一获取可连接点?如表7-1, 获得可连接点</span></font> </font> </p> <p> <font face="宋体"> <font size="3"> <b> <span lang="EN-US">Table 7-1</span> </b> <span lang="EN-US"> <i>Methods of the</i> IConnectionPointContainer<i> Interface</i></span> </font> </font> </p> <table style="WIDTH: 95%; mso-cellspacing: 1.5pt; mso-padding-alt: 3.75pt 3.75pt 3.75pt 3.75pt" cellpadding="0" width="95%" border="0"> <tbody> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; TEXT-ALIGN: center" align="center"> <font size="3"> <b> <i> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">Ҏ</span> </i> </b> <b> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </b> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; TEXT-ALIGN: center" align="center"> <font size="3"> <b> <i> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">描述</span> </i> </b> <b> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </b> </font> </p> <p> </p> </td> </tr> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font face="Times New Roman"> <font size="3"> <i> <span lang="EN-US">EnumConnectionPoints</span> </i> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font size="3"> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">列D可连接对象支持的全部可连接对?/span> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </p> <p> </p> </td> </tr> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font face="Times New Roman"> <font size="3"> <i> <span lang="EN-US">FindConnectionPoint</span> </i> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font size="3"> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">让客h询可q接对象关于它是否支持一个特D接口。客h定特D的接口Q可q接点)的接口标C?/span> <span lang="EN-US"> <font face="Times New Roman"> (IID) </font> </span> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。如果可q接对象支持此接口,q回</span> <font face="Times New Roman"> <i> <span lang="EN-US">IConnectionPoint</span> </i> <span lang="EN-US"> </span> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">接口的指针?/span> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </p> <p> </p> </td> </tr> </tbody> </table> <h2 style="MARGIN: auto 0cm"> <i> <span lang="EN-US"> <font face="宋体">IConnectionPoint</font> </span> </i> </h2> <p> <font face="宋体"> <font size="3">一旦客L道哪个连接点可被q接对象服务器支?span lang="EN-US">, 客户可建立同可q接对象的连接。客户通知可连接对象将要在全部事g中接攉些事?当客户不再需要接收来自可q接对象的事?客户解除对对象的通知. ?-2 展示?<i>IConnectionPoint</i> 接口可被客户q接? (大多数时?你将q接C仅表中头两个)</span></font> </font> </p> <p> <font face="宋体"> <font size="3"> <b> <span lang="EN-US">Table 7-2</span> </b> <span lang="EN-US"> <i>Methods of the </i>IConnectionPoint<i> Interface</i></span> </font> </font> </p> <table style="WIDTH: 95%; mso-cellspacing: 1.5pt; mso-padding-alt: 3.75pt 3.75pt 3.75pt 3.75pt" cellpadding="0" width="95%" border="0"> <tbody> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; TEXT-ALIGN: center" align="center"> <font size="3"> <b> <i> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">Ҏ</span> </i> </b> <b> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </b> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; TEXT-ALIGN: center" align="center"> <font size="3"> <b> <i> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">描述</span> </i> </b> <b> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </b> </font> </p> <p> </p> </td> </tr> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font face="Times New Roman"> <font size="3"> <i> <span lang="EN-US">Advise </span> </i> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font size="3"> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">在客户和可连接对象的某一个可q接炚w建立q接?/span> <font face="Times New Roman"> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">客户必须传递它的事件接收槽?/span> <font face="Times New Roman"> <i> <span lang="EN-US">IUnknown</span> </i> <span lang="EN-US"> </span> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">接口?/span> <font face="Times New Roman"> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">事g接收槽必d?/span> <font face="Times New Roman"> <i> <span lang="EN-US">IDispatch</span> </i> <span lang="EN-US"> </span> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">接口以接收事件?/span> <font face="Times New Roman"> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">典型?/span> <span lang="EN-US"> <font face="Times New Roman">,</font> </span> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">党课q接对象Ȁ发事Ӟ可连接对象将调用</span> <font face="Times New Roman"> <i> <span lang="EN-US">IDispatch</span> </i> <span lang="EN-US"> </span> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">接口?/span> <i> <span lang="EN-US"> <font face="Times New Roman">Invoke </font> </span> </i> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">Ҏ?/span> <font face="Times New Roman"> <i> <span lang="EN-US">Advise</span> </i> <span lang="EN-US"> </span> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">Ҏq回一?/span> <span lang="EN-US"> <font face="Times New Roman"> cookie </font> </span> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">Q当客户中断q接时候,调用</span> <i> <span lang="EN-US"> <font face="Times New Roman">Unadvise</font> </span> </i> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">Ҏ时候需要携带此</span> <font face="Times New Roman"> <span lang="EN-US">cookie</span> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> </tr> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font face="Times New Roman"> <font size="3"> <i> <span lang="EN-US">Unadvise </span> </i> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font size="3"> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">中断q接</span> <font face="Times New Roman"> <span lang="EN-US">.</span> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> </tr> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font face="Times New Roman"> <font size="3"> <i> <span lang="EN-US">GetConnectionInterface</span> </i> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font size="3"> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">q回p接点理的外发接口的</span> <span lang="EN-US"> <font face="Times New Roman">IID . <i>GetConnectionInterface </i></font> </span> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">Ҏ让客户将</span> <i> <span lang="EN-US"> <font face="Times New Roman">IConnectionPoint</font> </span> </i> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">译Z?/span> <font face="Times New Roman"> <span lang="EN-US">IID.</span> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> </tr> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font face="Times New Roman"> <font size="3"> <i> <span lang="EN-US">GetConnectionPointContainer </span> </i> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font size="3"> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">得到刻连接对象的</span> <font face="Times New Roman"> <i> <span lang="EN-US">IConnectionPointContainer</span> </i> <span lang="EN-US"> </span> </font> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">接口</span> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </p> <p> </p> </td> </tr> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font face="Times New Roman"> <font size="3"> <i> <span lang="EN-US">EnumConnections </span> </i> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent" valign="top"> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"> <font size="3"> <span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">枚D刻连接对象的当前可连接点</span> <font face="Times New Roman"> <span lang="EN-US">.</span> <span lang="EN-US" style="FONT-SIZE: 12pt; COLOR: black; FONT-FAMILY: 宋体"> <p> </p> </span> </font> </font> </p> <p> </p> </td> </tr> </tbody> </table> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 10.5pt; TEXT-INDENT: -10.5pt; mso-char-indent-count: -1.0; mso-char-indent-size: 10.5pt"> <span lang="EN-US"> <font size="3"> <font face="Times New Roman"> <p> </p> </font> </font> </span> </p> <p> </p> <h1 style="MARGIN: auto 0cm"> <font face="宋体">接收事g的途径</font> </h1> <p> <font size="3"> <font face="宋体">依靠开发工具你创徏客户应用E序<span lang="EN-US">,你可以接收事仉过不同的途径. 昄, 在Vb中接收事件同在VC中接收事件相比是如此不同和容??C++ 应用?你可以用不同的技术,通过使用 ATL, MFC, 或者标准C++.</span></font> </font> </p> <h2 style="MARGIN: auto 0cm"> <span lang="EN-US"> <font face="宋体">Visual Basic 中接收事?</font> </span> </h2> <p> <span lang="EN-US"> <font face="宋体" size="3">Visual Basic是创建大多数cd应用的最L的工? 所以我告诉你VB是处理事件最溶的工具时也不要惊奇. ATL ?Visual Basic CZ我们同样的工?但是ATLp了我4个小? ?Visual Basic 例子仅仅只花20 分钟.别说我错了—我是ATL, ?MFCQ?C++的忠实信?<span style="mso-spacerun: yes">  </span>其是你建立一个接口的时?但是 Visual Basic当徏立客户应用程序从cMIEq样的服务器接收事g时是伟大的工?</font> </span> </p> <p> <span lang="EN-US"> <font face="宋体" size="3">OK,如何从Visual Basic 应用E序中接收事Ӟ当宿主WebBrowser 控g,你不必做M特别的事. Visual Basic 在form上ؓWebBrowser 控g接收事g.你所需要做的全部事情就是未你要接收的Q何事件创Z个事件处理句?</font> </span> </p> <p> <font size="3"> <font face="宋体">你象创徏其他事g句柄一样创建句?span lang="EN-US"> (例如<i>Form_Load</i> event). 从Procedure下拉列表框中选择你象控制的句? 在事件句柄中,加入M你型在事件激发时执行的Q何代?</span></font> </font> </p> <p> <font size="3"> <font face="宋体">当自动化服务器时候接收事?span lang="EN-US">, 例如在VB应用中的Internet Explorer,q程直截了当.首先讄Ҏ务器的类型库的引? 你可以访问Project/References 菜单.之后Q采?i>WithEvents</i> 关键字声明服务器对象的变?举例, 如果你自动化Internet Explorer, 你将声明变量如下:</span></font> </font> </p> <table style="WIDTH: 95%; mso-cellspacing: 1.5pt; mso-padding-alt: 3.75pt 3.75pt 3.75pt 3.75pt" cellpadding="0" width="95%" border="0"> <tbody> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <pre> <span lang="EN-US"> <font face="黑体" size="2">Dim WithEvents InternetExplorer1 As InternetExplorer</font> </span> </pre> </td> </tr> </tbody> </table> <p> <font size="3"> <font face="宋体">下一步,采用<span lang="EN-US">new或者其?关键字创建实例变?Q如下::</span></font> </font> </p> <table style="WIDTH: 95%; mso-cellspacing: 1.5pt; mso-padding-alt: 3.75pt 3.75pt 3.75pt 3.75pt" cellpadding="0" width="95%" border="0"> <tbody> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <pre> <span lang="EN-US"> <font face="黑体" size="2">Set InternetExplorer1 = CreateObject("InternetExplorer.Application.1")</font> </span> </pre> </td> </tr> </tbody> </table> <p> <font size="3"> <font face="宋体">或?span lang="EN-US">:</span></font> </font> </p> <table style="WIDTH: 95%; mso-cellspacing: 1.5pt; mso-padding-alt: 3.75pt 3.75pt 3.75pt 3.75pt" cellpadding="0" width="95%" border="0"> <tbody> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <pre> <span lang="EN-US"> <font face="黑体" size="2">Set InternetExplorer1 = New InternetExplorer</font> </span> </pre> </td> </tr> </tbody> </table> <p> <font size="3"> <font face="宋体">当你采用以上途径生成实例接收事g<span lang="EN-US">, Visual Basic 自动Z初始化和理事g接收.你不必担心连接点问题QVBZ处理它们.</span></font> </font> </p> <p> <font size="3"> <font face="宋体">在你输入建立服务器的代码之后<span lang="EN-US">,你插入符合服务器事g的方法调? <span style="mso-spacerun: yes"> </span><span style="mso-spacerun: yes"> </span>举例来说, 如果你想控制由IEȀzȝ<i>DownloadBegin</i> event, 你应当声明类似如下的Ҏ声明:</span></font> </font> </p> <table style="WIDTH: 95%; mso-cellspacing: 1.5pt; mso-padding-alt: 3.75pt 3.75pt 3.75pt 3.75pt" cellpadding="0" width="95%" border="0"> <tbody> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <pre> <span lang="EN-US"> <font face="黑体" size="2">Private Sub InternetExplorer1_DownloadBegin()</font> </span> </pre> <pre> <span lang="EN-US"> <font size="2"> <font face="黑体"> <span style="mso-spacerun: yes">   </span>' Insert your best Visual Basic code here.</font> </font> </span> </pre> <pre> <span lang="EN-US"> <font face="黑体" size="2">End Sub</font> </span> </pre> </td> </tr> </tbody> </table> <p> <font size="3"> <font face="宋体">当你不再x收来自服务器的事Ӟ单设|变量ؓ<i><span lang="EN-US">Nothing</span></i><span lang="EN-US">:</span></font> </font> </p> <table style="WIDTH: 95%; mso-cellspacing: 1.5pt; mso-padding-alt: 3.75pt 3.75pt 3.75pt 3.75pt" cellpadding="0" width="95%" border="0"> <tbody> <tr> <td style="BORDER-RIGHT: #d4d0c8; PADDING-RIGHT: 3.75pt; BORDER-TOP: #d4d0c8; PADDING-LEFT: 3.75pt; PADDING-BOTTOM: 3.75pt; BORDER-LEFT: #d4d0c8; PADDING-TOP: 3.75pt; BORDER-BOTTOM: #d4d0c8; BACKGROUND-COLOR: transparent"> <pre> <span lang="EN-US"> <font face="黑体" size="2">Set InternetExplorer1 = Nothing</font> </span> </pre> </td> </tr> </tbody> </table> <img src ="http://www.shnenglu.com/tx7do/aggbug/8918.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/tx7do/" target="_blank">杨粼?/a> 2006-06-23 21:44 <a href="http://www.shnenglu.com/tx7do/articles/8918.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>如何对webbrowser和IE~程Q七Q?/title><link>http://www.shnenglu.com/tx7do/articles/8917.html</link><dc:creator>杨粼?/dc:creator><author>杨粼?/author><pubDate>Fri, 23 Jun 2006 13:43:00 GMT</pubDate><guid>http://www.shnenglu.com/tx7do/articles/8917.html</guid><wfw:comment>http://www.shnenglu.com/tx7do/comments/8917.html</wfw:comment><comments>http://www.shnenglu.com/tx7do/articles/8917.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.shnenglu.com/tx7do/comments/commentRss/8917.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/tx7do/services/trackbacks/8917.html</trackback:ping><description><![CDATA[     摘要: 加入高功能 本节展C如何加入高U功能到你的应用E序或者ActiveX控g.展C如何从一个ActiveX控g中访问Internet Explorer?IWebBrowser2Q以及如何从一个Web面的frame中获得WebBrowser 对象。将会展C实C些ƈ非容易实现的功能.本节有一定难?所有代码采用C++ 和COM实现,你应当有一定坚实的?..  <a href='http://www.shnenglu.com/tx7do/articles/8917.html'>阅读全文</a><img src ="http://www.shnenglu.com/tx7do/aggbug/8917.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/tx7do/" target="_blank">杨粼?/a> 2006-06-23 21:43 <a href="http://www.shnenglu.com/tx7do/articles/8917.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>如何对webbrowser和IE~程Q六Q?/title><link>http://www.shnenglu.com/tx7do/articles/8916.html</link><dc:creator>杨粼?/dc:creator><author>杨粼?/author><pubDate>Fri, 23 Jun 2006 13:42:00 GMT</pubDate><guid>http://www.shnenglu.com/tx7do/articles/8916.html</guid><wfw:comment>http://www.shnenglu.com/tx7do/comments/8916.html</wfw:comment><comments>http://www.shnenglu.com/tx7do/articles/8916.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.shnenglu.com/tx7do/comments/commentRss/8916.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/tx7do/services/trackbacks/8916.html</trackback:ping><description><![CDATA[     摘要: 使用VC++和COM API 管使用VC不像Vb中那么容易自动化IEQ但是也不太难,其是你理解了CON和COM API。无Z使用MFC, ATL, 或者标?C++自动化IEQ方法都是一样—你使用COM API来实? VC++中创Z个Internet Explorer实例包括要调用COM AP...  <a href='http://www.shnenglu.com/tx7do/articles/8916.html'>阅读全文</a><img src ="http://www.shnenglu.com/tx7do/aggbug/8916.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/tx7do/" target="_blank">杨粼?/a> 2006-06-23 21:42 <a href="http://www.shnenglu.com/tx7do/articles/8916.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>如何对webbrowser和IE~程Q五Q?http://www.shnenglu.com/tx7do/articles/8915.html杨粼?/dc:creator>杨粼?/author>Fri, 23 Jun 2006 13:42:00 GMThttp://www.shnenglu.com/tx7do/articles/8915.htmlhttp://www.shnenglu.com/tx7do/comments/8915.htmlhttp://www.shnenglu.com/tx7do/articles/8915.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/8915.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/8915.html阅读全文

]]>
如何对webbrowser和IE~程Q四Q?http://www.shnenglu.com/tx7do/articles/8914.html杨粼?/dc:creator>杨粼?/author>Fri, 23 Jun 2006 13:42:00 GMThttp://www.shnenglu.com/tx7do/articles/8914.htmlhttp://www.shnenglu.com/tx7do/comments/8914.htmlhttp://www.shnenglu.com/tx7do/articles/8914.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/8914.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/8914.html阅读全文

]]>
如何对webbrowser和IE~程Q三Q?http://www.shnenglu.com/tx7do/articles/8913.html杨粼?/dc:creator>杨粼?/author>Fri, 23 Jun 2006 13:41:00 GMThttp://www.shnenglu.com/tx7do/articles/8913.htmlhttp://www.shnenglu.com/tx7do/comments/8913.htmlhttp://www.shnenglu.com/tx7do/articles/8913.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/8913.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/8913.html阅读全文

]]>
如何对webbrowser和IE~程Q二Q?http://www.shnenglu.com/tx7do/articles/8912.html杨粼?/dc:creator>杨粼?/author>Fri, 23 Jun 2006 13:40:00 GMThttp://www.shnenglu.com/tx7do/articles/8912.htmlhttp://www.shnenglu.com/tx7do/comments/8912.htmlhttp://www.shnenglu.com/tx7do/articles/8912.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/8912.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/8912.html 调用 Navigate Ҏ?em>GoBack 以及 GoForward  要困?但如果你正仅仅导航到URL 且ƈ不传递Q何附加参? 它的调用很容易?举例来说, VB中导航到 Microsoft 主页, 可如?

WebBrowser1.Navigate "http://www.microsoft.com"

VB代码调用Navigate 如此Ҏ因ؓ所有参数出W一个参数外都可以是可? 如此相对照,VC++不可以省略Q何参? 如果你想使用VC++不是勇Q何特别的参数D?Microsoft?home page, 你必M递空?em>VARIANT l构?MFC 应用E序,你必d下调?Navigate

COleVariant vtEmpty;

m_webBrowser.Navigate(_T(
"http://www.microsoft.com"), &vtEmpty, &vtEmpty, &vtEmpty, &vtEmpty);

该例子展CZ?span lang="EN-US">MFC应用E序中控制WebBrowser控g. 我传递一个普通的字符串而替?BSTR 因ؓ MFC 提供了一?WebBrowser 控g的包装类,W一个蝲包装cM?em>LPCTSTR, 一个普通的字符? 其他参数为指?VARIANT l构的指针?如果你不x定Q何特别的参数, 别仅仅传?NULL —那样? 你的应用E序会招来崩溃。你必须传递一个空?em>VARIANT l构的指? 前面的代码用了 COleVariant c? 那是一个与 CComVariant cȝ似的c?a >?COleVariant 单包装了 VARIANT 使得VARIANT l构易于使用.

属?/strong> 现在你看C所有的 IwebBrowser 的方法,你大概向了解其属性?span lang="EN-US">(我是不是太苛求了?)  IWebBrowser 接口?0个属性,描述于表6-2. 我一已按?em>IWebBrowser  的Vtable中的字母序列出?/span>

Table 6-2. IWebBrowser 属性按照vtable排序

属?/span>

 

描述

 

Application

 

q回宿主 WebBrowser 控g的自动化对象 (IDispatch) 实现Q如果对象不可用Q则q回?/span> WebbOrwser 控g的自动化对象

 

Parent

 

q回 WebBrowser 控g的父控g的自动化实现 (IDispatch) Q通常是容?/span> 举例来讲 , Q您的宿L?/span> Internet Explorer H口?/span>

 

Container

 

q回 WebBrowser 控g容器的自动化对象 (IDispatch) 。通常Q该D回同 Parent 属性一L倹{?/span> .

 

Document

 

q回zd文档的自动化实现 (IDispatch) 。如?/span> HTML 当前昄?/span> WebBrowser Q?/span> Document 属性给Z存取 DHTML 对象模型的途径 .

 

TopLevelContainer

 

q回一个布值指C?/span> IE 是否?/span> WebBRowser 控g的顶U容器。在 words 中,如果 IE 是宿d用承需则返?/span> true

 

Type

 

q回已经?/span> WebBrowser 中装载的对象的类型。D例,如果 HTML document 被装?/span> , Type 返?/span> Microsoft HTML Document 5.0 . 如果文档?/span> Word 文档 , Type q回 Microsoft Word Document .

 

Left

 

. q回或设|控件在容器H口左边?/span>

 

Top

 

. q回或设|控件在容器H口剙边距

 

Width

 

q回或设|?/span> webbrowser 控g在窗口中的水qx向的向苏为单位宽?/span>

 

Height

 

q回或设|?/span> webbrowser 控g在窗口中的处|方向的向像素ؓ单位高度

 

LocationName

 

q回一?/span> WebBrowser 当前昄的资源名U的字符?/span> ( 换句话讲 , HTML ?/span> , Word 文档 , Q?/span> folder, 诸如此类 ) ?/span> 如果资源?/span> HTML ,字符串是标题。如果资源是文g或者文件夹Q字W串为文件名或者文件夹名?/span> 举例 , foo.doc Q?/span> Word 文档Q或?/span>   Temp Q?/span> temp directory. Q?/span>

 

LocationURL

 

q回 WebBrowser 正在昄的资源的 URL

 

Busy

 

q回一个布值指C?/span> WebBrowser 当前是否正在装入 URL. 。如果当前属性返?/span> true , 你可以?/span> Stop Ҏ取消代掉D?/span>

 

看完?span lang="EN-US"> 6-2, 清晰展示了你可用的属? 当中的一些可能需要更多的解释. IWebBrowser 使用的相当多的一个属性是 LocationURL, l出了当前你装入WebBrowserH口?URL?获取 LocationURL 值在VB中相当容易:

Dim strLocation

strLocation 
= WebBrowser1.LocationURL

Visual C++的MFC应用,  MFC 包装cM的访?em>LocationURL 很容? 你简单调?GetLocationURL Ҏ,该方法返回一?CString 对象. 当你惛_自动化IE中或者webBrowser的MFC应用中访?LocationURL when automating Internet Explorer or when hosting the WebBrowser control in a C++ application that's not built by using MFC, 你必调用携带一指向BSTR的指?em>?/em>BSTR 包含返回? 此处展示如何?C++中?

BSTR bstrURL;

m_pInternetExplorer
->get_LocationURL(&bstrURL);

 

存取 Document 属性在VB中相当容易,当定义一个变量后QD? HtmlDocQ? 值需?set ?Document 属性:

Set HtmlDoc = WebBrowser1.Document

MFC 中也很容?使用 MFC 包装cȝGetDocumentҎQ?br />

IDispatch* pDisp;

pDisp 
= m_webBrowser.GetDocument();
GetDocument q回指向代表文档 IDispatch 接口的指? 如果 GetDocument p|, 该对象将?em>NULL.

?span lang="EN-US">MFC C++ 应用或者Q何自动化IE的C++ 应用讉KDocument 属性就只能够采用调用COM的方?#8212;通过属性的get_Ҏ. (注艺属性实只读,所以这里无put_ Ҏ.) 当调?Document  ?em>get_ Ҏ,你传递一个接?IDispatch 的指?此处展示了如何调用:

IDispatch* pDisp;
HRESULT hr 
= m_pInternetExplorer->get_Document(&pDisp);                    

当用这些代?span lang="EN-US">,你可以?SUCCEEDED 宏( Win32 API的一部分Q? 以监调用是否成功。在试使用Idispatch接口前你应当信调用成功?/span>



]]>
如何对webbrowser和IE~程Q一Q?/title><link>http://www.shnenglu.com/tx7do/articles/8911.html</link><dc:creator>杨粼?/dc:creator><author>杨粼?/author><pubDate>Fri, 23 Jun 2006 13:40:00 GMT</pubDate><guid>http://www.shnenglu.com/tx7do/articles/8911.html</guid><wfw:comment>http://www.shnenglu.com/tx7do/comments/8911.html</wfw:comment><comments>http://www.shnenglu.com/tx7do/articles/8911.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.shnenglu.com/tx7do/comments/commentRss/8911.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/tx7do/services/trackbacks/8911.html</trackback:ping><description><![CDATA[     摘要: 一? 因ؓ工作~故Q需要研I对 IE ~程Q所以翻译了 MS 的有兌料,供参考? ...  <a href='http://www.shnenglu.com/tx7do/articles/8911.html'>阅读全文</a><img src ="http://www.shnenglu.com/tx7do/aggbug/8911.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/tx7do/" target="_blank">杨粼?/a> 2006-06-23 21:40 <a href="http://www.shnenglu.com/tx7do/articles/8911.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>vc调试l验http://www.shnenglu.com/tx7do/articles/6492.html杨粼?/dc:creator>杨粼?/author>Sun, 30 Apr 2006 09:26:00 GMThttp://www.shnenglu.com/tx7do/articles/6492.htmlhttp://www.shnenglu.com/tx7do/comments/6492.htmlhttp://www.shnenglu.com/tx7do/articles/6492.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/6492.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/6492.html       我们在做vc~程调试时经帔R到需要显C变量的内容之类的问题,在dos模式下我们简单用printf(...)p了,?a class="wordstyle" target="_blank">windows我们如何昄变量内容呢?大家肯定有许多方法如Q调试时讄断点Q用MessagBox什么的。我在开始用vcӞ也经帔R用这LҎ来调试,但遇C些不能用断点调试的程序时Q比如某些绘囄E序里需要在ondraw里计,没办法了,把变量写到文仉吧?太麻烦了Q还是看看仔l检查源代码吧!

        一个偶然的Z,我终于发Cwindows下类似printf的东东了Q那是_RPT?/p>

        大家在自己vc 的源E序里加上_RPT1(0,"i=%d\n",i);到debug模式下运行一下。好了,看到l果了吧Q那_RPT1能有几个参数吗?不行!哪要有两个参数怎么办?那就用_RPT2吧!其他的就自己试吧Q?/p>

        s6283@hotmail.com



]]>
VC调试入门http://www.shnenglu.com/tx7do/articles/6491.html杨粼?/dc:creator>杨粼?/author>Sun, 30 Apr 2006 09:26:00 GMThttp://www.shnenglu.com/tx7do/articles/6491.htmlhttp://www.shnenglu.com/tx7do/comments/6491.htmlhttp://www.shnenglu.com/tx7do/articles/6491.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/6491.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/6491.html阅读全文

]]>
高质量C++/C~程指南http://www.shnenglu.com/tx7do/articles/6136.html杨粼?/dc:creator>杨粼?/author>Mon, 24 Apr 2006 02:13:00 GMThttp://www.shnenglu.com/tx7do/articles/6136.htmlhttp://www.shnenglu.com/tx7do/comments/6136.htmlhttp://www.shnenglu.com/tx7do/articles/6136.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/6136.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/6136.html阅读全文

]]>
C++ ~程指南http://www.shnenglu.com/tx7do/articles/6133.html杨粼?/dc:creator>杨粼?/author>Mon, 24 Apr 2006 02:09:00 GMThttp://www.shnenglu.com/tx7do/articles/6133.htmlhttp://www.shnenglu.com/tx7do/comments/6133.htmlhttp://www.shnenglu.com/tx7do/articles/6133.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/6133.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/6133.html阅读全文

]]>
Windows消息目录http://www.shnenglu.com/tx7do/articles/5959.html杨粼?/dc:creator>杨粼?/author>Thu, 20 Apr 2006 09:32:00 GMThttp://www.shnenglu.com/tx7do/articles/5959.htmlhttp://www.shnenglu.com/tx7do/comments/5959.htmlhttp://www.shnenglu.com/tx7do/articles/5959.html#Feedback0http://www.shnenglu.com/tx7do/comments/commentRss/5959.htmlhttp://www.shnenglu.com/tx7do/services/trackbacks/5959.html1. WM_NULL=$0000:
2. WM_CREATE=$0001:    应用E序创徏一个窗?br />3. WM_DESTROY=$0002:    一个窗口被销?br />4. WM_MOVE=$0003: Ud一个窗?br />5. WM_SIZE=$0005:改变一个窗口的大小
6. WM_ACTIVATE=$0006: 一个窗口被ȀzL失去Ȁzȝ态;
7. WM_SETFOCUS=$0007: 获得焦点?br />8. WM_KILLFOCUS=$0008: 失去焦点
9. WM_ENABLE=$000A: 改变enable状?br />10. WM_SETREDRAW=$000B: 讄H口是否能重?br />11. WM_SETTEXT=$000C: 应用E序发送此消息来设|一个窗口的文本
12. WM_GETTEXT=$000D: 应用E序发送此消息来复13. 制对应窗口的文本到缓冲区
14. WM_GETTEXTLENGTH=$000E: 得到与一个窗口有关的文本的长度(?5. 包含I字W)
16. WM_PAINT=$000F: 要求一个窗口重画自?br />17. WM_CLOSE=$0010: 当一个窗口或应用E序要关闭时发送一个信?br />18. WM_QUERYENDSESSION=$0011: 当用户选择l束对话框或E序自己调用ExitWindows函数
19. WM_QUIT=$0012: 用来l束E序q行或当E序调用postquitmessage函数
20. WM_QUERYOPEN=$0013: 当用L口恢?1. 以前的大位|时Q?2. 把此消息发送给某个图标23. 
24. WM_ERASEBKGND=$0014: 当窗口背景必被擦除Ӟ例在H口改变大小Ӟ
25. WM_SYSCOLORCHANGE=$0015: 当系l颜色改变时Q?6. 发送此消息l所有顶U窗?br />27. WM_ENDSESSION=$0016:当系l进E发出WM_QUERYENDSESSION消息?此消息发送给应用E序,通知它对话是否结?br />28. WM_SYSTEMERROR=$0017: 
29. WM_SHOWWINDOW=$0018: 当隐藏或昄H口是发送此消息l这个窗?br />30. WM_ACTIVATEAPP=$001C: 发此消息l应用程序哪个窗口是ȀzȝQ?1. 哪个是非ȀzȝQ?br />32. WM_FONTCHANGE=$001D: 当系l的字体资源库变化时发送此消息l所有顶U窗?br />33. WM_TIMECHANGE=$001E: 当系l的旉变化时发送此消息l所有顶U窗?br />34. WM_CANCELMODE=$001F: 发送此消息来取消某U正在进行的摸态(操作Q?br />35. WM_SETCURSOR=$0020:  如果鼠标36. 引v光标37. 在某个窗口中Ud且鼠?8. 输入没有被捕hQ?9. 发消息l某个窗?br />40. WM_MOUSEACTIVATE=$0021: 当光?1. 在某个非ȀzȝH口中?2. 用户正按着鼠标43. 的某个键发送此消息l当前窗?br />44. WM_CHILDACTIVATE=$0022: 发送此消息lMDI子窗口当用户点击此窗口的?5. 题栏Q?6. 或当H口被激z,47. UdQ?8. 改变大小
49. WM_QUEUESYNC=$0023:  此消息由Z计算机的训练E序发送,50. 通过WH_JOURNALPALYBACK的hookE序分离出用戯入消?br />51. WM_GETMINMAXINFO=$0024: 此消息发送给H口当它要改变大小或位|;
52. WM_PAINTICON=$0026:  发送给最化H口当它图标53. 要被重?br />54. WM_ICONERASEBKGND=$0027:此消息发送给某个最化H口Q?5. 仅当它在d?6. 前它的背景必被重画
57. WM_NEXTDLGCTL=$0028: 发送此消息l一个对话框E序L改焦点位|?br />58. WM_SPOOLERSTATUS=$002A: 每当打印理列队增加或减一条作业时发出此消?br />59. WM_DRAWITEM=$002B:  当buttonQ?0. comboboxQ?1. listboxQ?2. menu的可视外观改变时发送此消息l这些空件的所有?br />63. WM_MEASUREITEM=$002C: 当button,combobox,listbox,listviewcontrol,ormenuitem被创建时发送此消息 l控件      的所有?br />64. WM_DELETEITEM=$002D: 当thelistbox或combobox被销毁或当某些项被删除通过             LB_DELETESTRING,LB_RESETCONTENT,CB_DELETESTRING,orCB_RESETCONTENT消息
65. WM_VKEYTOITEM=$002E: 此消息有一个LBS_WANTKEYBOARDINPUT风格的发出给它的所有者来响应WM_KEYDOWN消息
66. WM_CHARTOITEM=$002F:   此消息由一个LBS_WANTKEYBOARDINPUT风格的列表框发送给他的所有者来响应WM_CHAR消息
67. WM_SETFONT=$0030:  当绘制文本时E序发送此消息得到控g要用的颜?br />68. WM_GETFONT=$0031:  应用E序发送此消息得到当前控gl制文本的字?br />69. WM_SETHOTKEY=$0032:  应用E序发送此消息让一个窗口与一个热键相兌
70. WM_GETHOTKEY=$0033:  应用E序发送此消息来判断热键与某个H口是否有关?br />71. WM_QUERYDRAGICON=$0037: 此消息发送给最化H口Q?2. 当此H口要被拖放?3. 它的cM没有定义图标74. Q?5. 应用E序        能返回一个图?6. 或光?7. 的句柄,78. 当用h攑֛?9. 时系l显C个图?0. 或光?1. 
82. WM_COMPAREITEM=$0039: 发送此消息来判定combobox或listbox新增加的的相对位置
83. WM_GETOBJECT=$003D:  
84. WM_COMPACTING=$0041: 昄内存已经很少?br />85. WM_WINDOWPOSCHANGING=$0046: 发送此消息l那个窗口的大小和位|将要被改变Ӟ86. 来调用setwindowpos函数或        其它窗口管理函?br />87. WM_WINDOWPOSCHANGED=$0047: 发送此消息l那个窗口的大小和位|已l被改变Ӟ88. 来调用setwindowpos函数或        其它窗口管理函?br />89. WM_POWER=$0048:  (适用?6位的windowsQ 当pȝ要q入暂停状态时发送此消息
90. WM_COPYDATA=$004A:  当一个应用程序传递数据给另一个应用程序时发送此消息
91. WM_CANCELJOURNAL=$004B: 当某个用户取消程序日志激zȝ态,92. 提交此消息给E序
93. WM_NOTIFY=$004E:   当某个控件的某个事g已经发生或这个控仉要得C些信息时Q?4. 发送此消息l它的父H口
95. WM_INPUTLANGCHANGEREQUEST=$0050: 当用户选择某种输入语言Q?6. 或输入语a的热键改?br />97. WM_INPUTLANGCHANGE=$0051: 当^台现场已l被改变后发送此消息l受影响的最H口
98. WM_TCARD=$0052:  当程序已l初始化windows帮助例程时发送此消息l应用程?br />99. WM_HELP=$0053: 此消息显C用h下了F1Q?00. 如果某个菜单是激zȝQ?01. 发送此消息个此H口兌的菜?否则  ?发送给有焦点的H口Q?02. 如果当前都没有焦点,103. 把此消息发送给当前ȀzȝH口
104. WM_USERCHANGED=$0054: 当用户已l登入或退出后发送此消息l所有的H口Q?05. 当用L入或退出时pȝ更新用   户的具体设|信息,106. 在用h新设|时pȝ马上发送此消息Q?br />107. WM_NOTIFYFORMAT=$0055: 公用控gQ?08. 自定义控件和他们的父H口通过此消息来判断控g是用ANSIq是    UNICODEl构在WM_NOTIFY消息Q?09. 使用此控件能使某个控件与它的父控件之间进行相互通信
110. WM_CONTEXTMENU=$007B: 当用h个窗口中点击了一下右键就发送此消息l这个窗?br />111. WM_STYLECHANGING=$007C: 当调用SETWINDOWLONG函数要改变一个或多个H口的风格时发送此消息l那个窗?br />112. WM_STYLECHANGED=$007D: 当调用SETWINDOWLONG函数一个或多个H口的风格后发送此消息l那个窗?br />113. WM_DISPLAYCHANGE=$007E: 当显C器的分辨率改变后发送此消息l所有的H口
114. WM_GETICON=$007F:  此消息发送给某个H口来返回与某个H口有关q的大图?15. 或小图标116. 的句柄;
117. WM_SETICON=$0080:  E序发送此消息让一个新的大图标118. 或小图标119. 与某个窗口关联;
120. WM_NCCREATE=$0081:  当某个窗口第一ơ被创徏Ӟ121. 此消息在WM_CREATE消息发送前发送;
122. WM_NCDESTROY=$0082:  此消息通知某个H口Q?23. 非客户区正在销?br />124. WM_NCCALCSIZE=$0083: 当某个窗口的客户区域必须被核时发送此消息
125. WM_NCHITTEST=$0084:   Ud鼠标126. Q?27. 按住或释N?28. 时发?br />129. WM_NCPAINT=$0085:  E序发送此消息l某个窗口当它(H口Q的框架必须被绘制时Q?br />130. WM_NCACTIVATE=$0086: 此消息发送给某个H口仅当它的非客户区需要被改变来显C是Ȁz还是非Ȁzȝ态;
131. WM_GETDLGCODE=$0087:   发送此消息l某个与对话框程序关联的控gQ?32. widdows控制方位键和TAB键输入q入    此控仉过响应WM_GETDLGCODE消息Q?33. 应用E序可以把他当成一个特D的输入控gq能处理?br />134. WM_NCMOUSEMOVE=$00A0: 当光?35. 在一个窗口的非客户区内移动时发送此消息l这个窗口file: 非客户区为:   H体的标136. 题栏及窗的边框体
137. WM_NCLBUTTONDOWN=$00A1: 当光?38. 在一个窗口的非客户区?39. 时按下鼠?40. 左键时提交此消息
141. WM_NCLBUTTONUP=$00A2: 当用户释N?42. 左键?43. 时光?44. 某个H口在非客户区十发送此消息Q?br />145. WM_NCLBUTTONDBLCLK=$00A3:当用户双击鼠?46. 左键?47. 时光?48. 某个H口在非客户区十发送此消息
149. WM_NCRBUTTONDOWN=$00A4: 当用h下鼠?50. 右键?51. 时光?52. 又在H口的非客户区时发送此消息
153. WM_NCRBUTTONUP=$00A5: 当用户释N?54. 右键?55. 时光?56. 又在H口的非客户区时发送此消息
157. WM_NCRBUTTONDBLCLK=$00A6:当用户双击鼠?58. 右键?59. 时光?60. 某个H口在非客户区十发送此消息
161. WM_NCMBUTTONDOWN=$00A7: 当用h下鼠?62. 中键?63. 时光?64. 又在H口的非客户区时发送此消息
165. WM_NCMBUTTONUP=$00A8: 当用户释N?66. 中键?67. 时光?68. 又在H口的非客户区时发送此消息
169. WM_NCMBUTTONDBLCLK=$00A9:当用户双击鼠?70. 中键?71. 时光?72. 又在H口的非客户区时发送此消息
173. WM_KEYFIRST=$0100: 
174. WM_KEYDOWN=$0100: file: 按下一个键
175. WM_KEYUP=$0101:  file: 释放一个键
176. WM_CHAR=$0102:  file: 按下某键Q?77. q已发出WM_KEYDOWNQ?78. WM_KEYUP消息
179. WM_DEADCHAR=$0103: 当用translatemessage函数译WM_KEYUP消息时发送此消息l拥有焦点的H口
180. WM_SYSKEYDOWN=$0104:当用h住ALT键同181. 时按下其它键时提交此消息l拥有焦点的H口Q?br />182. WM_SYSKEYUP=$0105: 当用户释放一个键?83. 时ALT键还按着时提交此消息l拥有焦点的H口
184. WM_SYSCHAR=$0106: 当WM_SYSKEYDOWN消息被TRANSLATEMESSAGE函数译后提交此消息l拥有焦点的H口
185. WM_SYSDEADCHAR=$0107: 当WM_SYSKEYDOWN消息被TRANSLATEMESSAGE函数译后发送此消息l拥有焦点的H口
186. WM_INITDIALOG=$0110: 在一个对话框E序被显C前发送此消息l它,常用此消息初始化控g和执行其它Q?br />187. WM_COMMAND=$0111:  当用户选择一条菜单命令项或当某个控g发送一条消息给它的父窗口,188. 一个快捷键被翻?br />189. WM_SYSCOMMAND=$0112: 当用户选择H口菜单的一条命令或当用户选择最大化或最化旉个窗口会收到此消?br />190. WM_TIMER=$0113:      发生了定时器事g
191. WM_HSCROLL=$0114:  当一个窗口标192. 准水qx动条产生一个滚动事件时发送此消息l那个窗口,193. 也发送给拥有它的控g
194. WM_VSCROLL=$0115:  当一个窗口标195. 准垂直滚动条产生一个滚动事件时发送此消息l那个窗口也Q?96. 发送给拥有它的控g
197. WM_INITMENU=$0116: 当一个菜单将要被ȀzL发送此消息Q?98. 它发生在用户菜单条中的某Ҏ按下某个菜单键,199.         它允许程序在昄前更改菜?br />200. WM_INITMENUPOPUP=$0117: 当一个下拉菜单或子菜单将要被ȀzL发送此消息Q?01. 它允许程序在它显C前更改菜单Q?02.        ?03. ?04. 要改变全?br />205. WM_MENUSELECT=$011F: 当用户选择一条菜单项时发送此消息l菜单的所有者(一般是H口Q?br />206. WM_MENUCHAR=$0120:  当菜单已被激zȝh下了某个键(?07. ?08. 于加速键Q,209. 发送此消息l菜单的所有者;
210. WM_ENTERIDLE=$0121:  当一个模态对话框或菜单进入空载状态时发送此消息l它的所有者,211. 一个模态对话框       或菜单进入空载状态就是在处理一条或几条先前的消息后没有消息它的列队中等?br />212. WM_MENURBUTTONUP=$0122: WM_MENUDRAG=$0123: WM_MENUGETOBJECT=$0124: WM_UNINITMENUPOPUP=$0125:
213. WM_MENUCOMMAND=$0126: WM_CHANGEUISTATE=$0127:WM_UPDATEUISTATE=$0128:WM_QUERYUISTATE=$0129:
214. WM_CTLCOLORMSGBOX=$0132: 在windowsl制消息框前发送此消息l消息框的所有者窗口,215. 通过响应q条            消息Q?16. 所有者窗口可以通过使用l定的相xC?17. 的句柄来讄消息框的文本和背景颜?br />218. WM_CTLCOLOREDIT=$0133: 当一个编辑型控g要被绘制时发送此消息l它的父H口:通过响应q条消息,所有者窗口可以通过使用l定的相xC?19. 的句柄来讄~辑框的文本和背景颜?br />220. WM_CTLCOLORLISTBOX=$0134:当一个列表框控g要被绘制前发送此消息l它的父H口Q通过响应q条息,221. 所有者窗口可以通过使用l定的相xC?22. 的句柄来讄列表框的文本和背景颜?br />223. WM_CTLCOLORBTN=$0135: 当一个按钮控件将要被l制时发送此消息l它的父H口Q通过响应q条消息Q?24. 所有者       窗口可以通过使用l定的相xC?25. 的句柄来讄按纽的文本和背景颜色
226. WM_CTLCOLORDLG=$0136: 当一个对话框控g要被绘制前发送此消息l它的父H口Q通过响应q条消息Q?27. 所有       者窗口可以通过使用l定的相xC?28. 的句柄来讄对话框的文本背景颜色
229. WM_CTLCOLORSCROLLBAR=$0137: 当一个滚动条控g要被绘制时发送此消息l它的父H口Q通过响应q条消息Q?30.          所有者窗口可以通过使用l定的相xC?31. 的句柄来讄滚动条的背景颜色
232. WM_CTLCOLORSTATIC=$0138: 当一个静态控件将要被l制时发送此消息l它的父H口Q通过响应q条消息Q?33. 所        有者窗口可以通过使用l定的相xC?34. 的句柄来讄静态控件的文本和背景颜?br />235. WM_MOUSEMOVE=$0200:     Ud鼠标236. 
237. WM_LBUTTONDOWN=$0201    按下鼠标238. 左键
239. WM_LBUTTONUP=$0202:    释放鼠标240. 左键
241. WM_LBUTTONDBLCLK=$0203:     双击鼠标242. 左键
243. WM_RBUTTONDOWN=$0204:   按下鼠标244. 右键
245. WM_RBUTTONUP=$0205:    释放鼠标246. 右键
247. WM_RBUTTONDBLCLK=$0206:   双击鼠标248. 右键
249. WM_MBUTTONDOWN=$0207:   按下鼠标250. 中键
251. WM_MBUTTONUP=$0208:    释放鼠标252. 中键
253. WM_MBUTTONDBLCLK=$0209:   双击鼠标254. 中键
255. WM_MOUSEWHEEL=$020A:  当鼠?56. 轮子转动时发送此消息个当前有焦点的控?br />257. WM_PARENTNOTIFY=$0210: 当MDI子窗口被创徏或被销毁,258. 或用h了一下鼠?59. 键?60. 光标261. 在子H口上时发送此消       息l它的父H口
262. WM_ENTERMENULOOP=$0211: 发送此消息通知应用E序的主H口that已经q入了菜单@环模?br />263. WM_EXITMENULOOP=$0212: 发送此消息通知应用E序的主H口that已退Z菜单循环模式
264. WM_NEXTMENU=$0213:
265. WM_SIZING=532:   当用h在调整窗口大时发送此消息l窗口;通过此消息应用程序可以监视窗口大       和位置也可以修改他?br />266. WM_CAPTURECHANGED=533: 发送此消息l窗口当它失LL鼠标267. Ӟ
268. WM_MOVING=534:   当用户在UdH口时发送此消息Q?69. 通过此消息应用程序可以监视窗口大和位置也可       以修改他们;
270. WM_POWERBROADCAST=536: 此消息发送给应用E序来通知它有关电源管理事Ӟ
271. WM_DEVICECHANGE=537:  当设?72. 的硬仉|改变时发送此消息l应用程序或讑֤273. 驱动E序
274. WM_IME_STARTCOMPOSITION=$010D: 
275. WM_IME_ENDCOMPOSITION=$010E:
276. WM_IME_COMPOSITION=$010F:
277. WM_IME_KEYLAST=$010F:
278. WM_IME_SETCONTEXT=$0281:
279. WM_IME_NOTIFY=$0282:
280. WM_IME_CONTROL=$0283:
281. WM_IME_COMPOSITIONFULL=$0284:
282. WM_IME_SELECT=$0285:
283. WM_IME_CHAR=$0286:
284. WM_IME_REQUEST=$0288:
285. WM_IME_KEYDOWN=$0290:
286. WM_IME_KEYUP=$0291:
287. WM_MDICREATE=$0220:  应用E序发送此消息l多文档的客L口来创徏一个MDI子窗?br />288. WM_MDIDESTROY=$0221: 应用E序发送此消息l多文档的客L口来关闭一个MDI子窗?br />289. WM_MDIACTIVATE=$0222: 应用E序发送此消息l多文档的客L口通知客户H口Ȁzd一个MDI子窗口,290. 当客       L口收到此消息后,291. 它发出WM_MDIACTIVE消息lMDI子窗口(未激z)ȀzdQ?br />292. WM_MDIRESTORE=$0223: E序发送此消息lMDI客户H口让子H口从最大最化恢复293. 到原来大?br />294. WM_MDINEXT=$0224:  E序发送此消息lMDI客户H口ȀzM一个或前一个窗?br />295. WM_MDIMAXIMIZE=$0225: E序发送此消息lMDI客户H口来最大化一个MDI子窗口;
296. WM_MDITILE=$0226:  E序发送此消息lMDI客户H口以^铺方式重新排列所有MDI子窗?br />297. WM_MDICASCADE=$0227: E序发送此消息lMDI客户H口以层叠方式重新排列所有MDI子窗?br />298. WM_MDIICONARRANGE=$0228: E序发送此消息lMDI客户H口重新排列所有最化的MDI子窗?br />299. WM_MDIGETACTIVE=$0229:    E序发送此消息lMDI客户H口来找到激zȝ子窗口的句柄
300. WM_MDISETMENU=$0230:  E序发送此消息lMDI客户H口用MDI菜单代替子窗口的菜单
301. WM_ENTERSIZEMOVE=$0231: 
302. WM_EXITSIZEMOVE=$0232:
303. WM_DROPFILES=$0233:
304. WM_MDIREFRESHMENU=$0234:
305. WM_MOUSEHOVER=$02A1:
306. WM_MOUSELEAVE=$02A3:
307. WM_CUT=$0300:    E序发送此消息l一个编辑框或combobox来删除当前选择的文?br />308. WM_COPY=$0301:   E序发送此消息l一个编辑框或combobox来复309. 制当前选择的文本到剪脓?br />310. WM_PASTE=$0302:   E序发送此消息leditcontrol或combobox从剪贴板中得到数?br />311. WM_CLEAR=$0303:   E序发送此消息leditcontrol或combobox清除当前选择的内容;
312. WM_UNDO=$0304:   E序发送此消息leditcontrol或combobox撤消最后一ơ操?br />313. WM_RENDERFORMAT=$0305Q?br />314. WM_RENDERALLFORMATS=$0306:
315. WM_DESTROYCLIPBOARD=$0307: 当调用ENPTYCLIPBOARD函数时发送此消息l剪贴板的所有?br />316. WM_DRAWCLIPBOARD=$0308:  当剪贴板的内容变化时发送此消息l剪贴板观察铄W一个窗口;它允许用剪脓        板观察窗口来昄剪脓板的新内容;
317. WM_PAINTCLIPBOARD=$0309:  当剪贴板包含CF_OWNERDIPLAY格式的数据ƈ且剪贴板观察H口的客户区需要重        画;
318. WM_VSCROLLCLIPBOARD=$030A:
319. WM_SIZECLIPBOARD=$030B:  当剪贴板包含CF_OWNERDIPLAY格式的数据ƈ且剪贴板观察H口的客户区域的大小        已经改变是此消息通过剪脓板观察窗口发送给剪脓板的所有者;
320. WM_ASKCBFORMATNAME=$030C:  通过剪脓板观察窗口发送此消息l剪贴板的所有者来h一个CF_OWNERDISPLAY        格式的剪贴板的名321. ?br />322. WM_CHANGECBCHAIN=$030D:  当一个窗口从剪脓板观察链中移L发送此消息l剪贴板观察铄W一个窗口;
323. WM_HSCROLLCLIPBOARD=$030E: 此消息通过一个剪贴板观察H口发送给剪脓板的所有者;它发生在当剪贴板包含        CFOWNERDISPALY格式的数据ƈ且有个事件在剪脓板观察窗的水qx动条上;所有        者应滚动剪脓板图象ƈ更新滚动条的|
324. WM_QUERYNEWPALETTE=$030F:  此消息发送给要收到焦点的窗口,325. 此消息能使窗口在收到焦点时同326. 时有Z实        现他的逻辑调色?br />327. WM_PALETTEISCHANGING=$0310:     当一个应用程序正要实现它的逻辑调色板时发此消息通知所有的应用E序
328. WM_PALETTECHANGED=$0311:  此消息在一个拥有焦点的H口实现它的逻辑调色板后发送此消息l所有顶Uƈ重        叠的窗口,329. 以此来改变系l调色板
330. WM_HOTKEY=$0312:    当用h下由REGISTERHOTKEY函数注册的热键时提交此消?br />331. WM_PRINT=791:     应用E序发送此消息仅当WINDOWS或其它应用程序发Z个请求要求绘制一个应用程序的一部分Q?br />332. WM_PRINTCLIENT=792: 
333. WM_HANDHELDFIRST=856:
334. WM_HANDHELDLAST=863:
335. WM_PENWINFIRST=$0380:
336. WM_PENWINLAST=$038F:
337. WM_COALESCE_FIRST=$0390:
338. WM_COALESCE_LAST=$039F:
339. WM_DDE_FIRST=$03E0:
340. WM_DDE_INITIATE=WM_DDE_FIRST+0:  一个DDE客户E序提交此消息开始一个与?41. 务器E序的会话来响应那个?42. 定的E序和主题名343. Q?br />344. WM_DDE_TERMINATE=WM_DDE_FIRST+1: 一个DDE应用E序(无论是客戯是服345. 务器)提交此消息来l止一个会话;
346. WM_DDE_ADVISE=WM_DDE_FIRST+2:  一个DDE客户E序提交此消息给一个DDE?47. 务程序来h?48. 务器每当敊W         据Ҏ变时更新?br />349. WM_DDE_UNADVISE=WM_DDE_FIRST+3:  一个DDE客户E序通过此消息通知一个DDE?50. 务程序不351. 更新?52. 定的Ҏ          一个特D的剪脓板格式的?br />353. WM_DDE_ACK=WM_DDE_FIRST+4:  此消息通知一个DDEQ动态数据交换)E序已收到ƈ正在处理WM_DDE_POKE,WM_DDE_EXECUTE,WM_DDE_DATA,WM_DDE_ADVISE,WM_DDE_UNADVISE,orWM_DDE_INITIAT消息WM_DDE_DATA=WM_DDE_FIRST+5:一个DDE?54. 务程序提交此消息lDDE客户E序来传递个一数据给客户或通知客户的一条可用数据项
355. WM_DDE_REQUEST=WM_DDE_FIRST+6: 一个DDE客户E序提交此消息给一个DDE?56. 务程序来h一个数据项的|
357. WM_DDE_POKE=WM_DDE_FIRST+7:  一个DDE客户E序提交此消息给一个DDE?58. 务程序,359. 客户使用此消息来h?60. 务器接收一个未l同361. 意的数据;?62. 务器通过{复363. WM_DDE_ACK消息提示是否它接收这个数据项Q?br />364. WM_DDE_EXECUTE=WM_DDE_FIRST+8: 一个DDE客户E序提交此消息给一DDE?65. 务程序来发送一个字W串l服366. 务器让它象串行命令一栯处理,?67. 务器通过提交WM_DDE_ACK消息来作回应Q?br />368. WM_DDE_LAST=WM_DDE_FIRST+8:  
369. WM_APP=$8000:
370. WM_USER=$0400: 此消息能帮助应用E序自定义私有消息;
                                  /
通知消息(Notificationmessage)是指q样一U消息,一个窗口内的子控g发生了一些事情,需要通知父窗口。通知消息只适用于标准的H口控g如按钮、列表框、组合框、编辑框Q以及Windows95公共控g如树状视图、列表视囄。例如,单击或双M个控件、在控g中选择部分文本、操作控件的
滚动条都会生通知消息?br />371. 按扭
372. BN_CLICKED  file: 用户单击了按?br />373. BN_DISABLE  file: 按钮被禁?br />374. BN_DOUBLECLICKED file: 用户双击了按?br />375. BN_HILITE file: 用户加亮了按?br />376. BN_PAINT 按钮应当重画
377. BN_UNHILITE  加亮应当Ll合?br />378. CBN_CLOSEUP  l合框的列表框被关闭
379. CBN_DBLCLK  用户双击了一个字W串
380. CBN_DROPDOWN l合框的列表框被拉出
381. CBN_EDITCHANGE 用户修改了编辑框中的文本
382. CBN_EDITUPDATE ~辑框内的文本即更?br />383. CBN_ERRSPACE l合框内存不384. ?br />385. CBN_KILLFOCUS l合框失去输入焦?br />386. CBN_SELCHANGE 在组合框中选择了一?br />387. CBN_SELENDCANCEL 用户的选择应当被取?br />388. CBN_SELENDOK  用户的选择是合法的
389. CBN_SETFOCUS  l合框获得输入焦点编辑框
390. EN_CHANGE   ~辑框中的文本己更新
391. EN_ERRSPACE   ~辑框内存不392. ?br />393. EN_HSCROLL   用户点击了水qx动条
394. EN_KILLFOCUS  ~辑框正在失去输入焦?br />395. EN_MAXTEXT   插入的内容被截断
396. EN_SETFOCUS   ~辑框获得输入焦?br />397. EN_UPDATE   ~辑框中的文本将要更?br />398. EN_VSCROLL   用户点击了垂直滚动条消息含义
列表?br />399. LBN_DBLCLK   用户双击了一?br />400. LBN_ERRSPACE  列表框内存不401. ?br />402. LBN_KILLFOCUS  列表框正在失去输入焦?br />403. LBN_SELCANCEL  选择被取?br />404. LBN_SELCHANGE  选择了另一?br />405. LBN_SETFOCUS  列表框获得输入焦?img src ="http://www.shnenglu.com/tx7do/aggbug/5959.html" width = "1" height = "1" />

]]>
þ޸ۿ| þþþƷһ| þþƷУСŮ| þþƷĻ| Ʒպҹþ| ݺۺϾþۺ88| ȫþվ| ҹӰԺþþƷѿһ | 99þþƷһ| ޹㽶þþþþ| þۺϺݺۺϾþۺ88| þþƷ޾Ʒŷ| þùȾƷҰAV| þþþavӰ| 99þù¶Ʒ| ˾þô߽ӰԺ95| 㽶þҹɫƷ2020| þ㽶ۺɫһۺɫ88| ɫۺϾþþþ| һþƵ| þþ91뾫ƷHD| ݺݺݾþ| þþ㽶ۺϼձ| ޹徫Ʒ߾þ| ҹƷþþþþžŵӰ| 99reþþƷҳ2020| ԭƷ99þþƷ66| ŷۺϾþͼƬ| þù| þþþӰԺ| ޹Ʒþþþþ| 97ȾþƵƷ99| 97þþþ޾Ʒר | 91ƷۺϾþ| Ʒ99þþþþ鶹| vĻþ| ŮƷþþ| Ʒvaþþþþþ| 2020¾þþӾƷ| þþƷƷƷ| ƷƵþþ|