<!-- @font-face {font-family:Wingdings; panose-1:5 0 0 0 0 0 0 0 0 0; mso-font-charset:2; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:0 268435456 0 0 -2147483648 0;} @font-face {font-family:SimSun; panose-1:2 1 6 0 3 1 1 1 1 1; mso-font-alt:宋體; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:3 135135232 16 0 262145 0;} @font-face {font-family:SimHei; panose-1:2 1 6 0 3 1 1 1 1 1; mso-font-alt:黑體; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:"Cambria Math"; panose-1:2 4 5 3 5 4 6 3 2 4; mso-font-charset:0; mso-generic-font-family:roman; mso-font-pitch:variable; mso-font-signature:-1610611985 1107304683 0 0 159 0;} @font-face {font-family:方正美黑簡體; mso-font-alt:"Arial Unicode MS"; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:方正楷體簡體; mso-font-alt:"Arial Unicode MS"; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:方正大标宋簡體; mso-font-alt:"Arial Unicode MS"; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:FangSong_GB2312; mso-font-charset:134; mso-generic-font-family:modern; mso-font-pitch:fixed; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:Impact; panose-1:2 11 8 6 3 9 2 5 2 4; mso-font-charset:0; mso-generic-font-family:swiss; mso-font-pitch:variable; mso-font-signature:647 0 0 0 159 0;} @font-face {font-family:"/@SimSun"; panose-1:2 1 6 0 3 1 1 1 1 1; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:3 135135232 16 0 262145 0;} @font-face {font-family:"/@SimHei"; panose-1:2 1 6 0 3 1 1 1 1 1; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:"/@方正楷體簡體"; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:"/@方正大标宋簡體"; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:"/@FangSong_GB2312"; mso-font-charset:134; mso-generic-font-family:modern; mso-font-pitch:fixed; mso-font-signature:1 135135232 16 0 262144 0;} @font-face {font-family:"/@方正美黑簡體"; mso-font-charset:134; mso-generic-font-family:auto; mso-font-pitch:variable; mso-font-signature:1 135135232 16 0 262144 0;} p.MsoNormal, li.MsoNormal, div.MsoNormal {mso-style-unhide:no; mso-style-qformat:yes; mso-style-parent:""; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} h1 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 1 Char"; mso-style-next:Normal; margin-top:30.0pt; margin-right:0mm; margin-bottom:30.0pt; margin-left:0mm; text-align:center; mso-line-height-alt:15.5pt; mso-pagination:lines-together; page-break-after:avoid; mso-outline-level:1; mso-layout-grid-align:none; font-size:20.0pt; mso-bidi-font-size:10.5pt; font-family:方正美黑簡體; mso-font-kerning:22.0pt; mso-fareast-language:ZH-CN; font-weight:normal;} h2 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 2 Char"; mso-style-next:Normal; margin-top:20.0pt; margin-right:0mm; margin-bottom:20.0pt; margin-left:0mm; text-align:center; mso-line-height-alt:15.5pt; mso-pagination:lines-together; page-break-after:avoid; mso-outline-level:2; mso-layout-grid-align:none; font-size:16.0pt; mso-bidi-font-size:15.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:方正楷體簡體; mso-fareast-language:ZH-CN; font-weight:normal;} h3 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 3 Char"; mso-style-next:Normal; margin-top:15.0pt; margin-right:0mm; margin-bottom:15.0pt; margin-left:0mm; text-align:justify; text-justify:inter-ideograph; line-height:15.5pt; mso-pagination:lines-together; page-break-after:avoid; mso-outline-level:3; mso-layout-grid-align:none; font-size:13.0pt; mso-bidi-font-size:10.5pt; font-family:"Arial","sans-serif"; mso-fareast-font-family:SimHei; mso-fareast-language:ZH-CN; font-weight:normal;} h4 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 4 Char"; mso-style-next:Normal; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.1pt; mso-char-indent-count:2.0; line-height:15.5pt; mso-pagination:none; mso-outline-level:4; mso-layout-grid-align:none; font-size:10.5pt; mso-bidi-font-size:10.0pt; font-family:"Times New Roman","serif"; mso-fareast-language:ZH-CN;} h5 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 5 Char"; mso-style-next:Normal; margin-top:14.0pt; margin-right:0mm; margin-bottom:14.5pt; margin-left:0mm; text-align:justify; text-justify:inter-ideograph; text-indent:0mm; line-height:156%; mso-pagination:lines-together; page-break-after:avoid; mso-outline-level:5; mso-list:l5 level5 lfo1; mso-layout-grid-align:none; font-size:14.0pt; font-family:"Times New Roman","serif"; mso-fareast-language:ZH-CN;} h6 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 6 Char"; mso-style-next:Normal; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; page-break-after:avoid; mso-outline-level:6; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimHei; mso-fareast-language:ZH-CN; font-weight:normal;} p.MsoHeading7, li.MsoHeading7, div.MsoHeading7 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 7 Char"; mso-style-next:Normal; margin-top:12.0pt; margin-right:0mm; margin-bottom:3.2pt; margin-left:64.8pt; text-align:justify; text-justify:inter-ideograph; text-indent:-64.8pt; line-height:16.0pt; mso-pagination:lines-together; page-break-after:avoid; mso-outline-level:7; mso-list:l4 level7 lfo5; tab-stops:list 64.8pt; mso-layout-grid-align:none; font-size:10.5pt; mso-bidi-font-size:10.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN; font-weight:bold; mso-bidi-font-weight:normal;} p.MsoHeading8, li.MsoHeading8, div.MsoHeading8 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 8 Char"; mso-style-next:Normal; margin-top:12.0pt; margin-right:0mm; margin-bottom:3.2pt; margin-left:72.0pt; text-align:justify; text-justify:inter-ideograph; text-indent:-72.0pt; line-height:16.0pt; mso-pagination:lines-together; page-break-after:avoid; mso-outline-level:8; mso-list:l4 level8 lfo5; tab-stops:list 72.0pt; mso-layout-grid-align:none; font-size:10.5pt; mso-bidi-font-size:10.0pt; font-family:"Arial","sans-serif"; mso-fareast-font-family:SimHei; mso-bidi-font-family:"Times New Roman"; mso-fareast-language:ZH-CN;} p.MsoHeading9, li.MsoHeading9, div.MsoHeading9 {mso-style-unhide:no; mso-style-qformat:yes; mso-style-link:"Heading 9 Char"; margin-top:1.0pt; margin-right:0mm; margin-bottom:0mm; margin-left:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:13.0pt; mso-pagination:lines-together; mso-outline-level:9; mso-list:l0 level9 lfo4; mso-layout-grid-align:none; font-size:10.5pt; mso-bidi-font-size:10.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoToc1, li.MsoToc1, div.MsoToc1 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoToc2, li.MsoToc2, div.MsoToc2 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:21.0pt; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:2.0gd; mso-para-margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; mso-pagination:none; font-size:10.5pt; mso-bidi-font-size:12.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-font-kerning:1.0pt; mso-fareast-language:ZH-CN;} p.MsoToc3, li.MsoToc3, div.MsoToc3 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:42.0pt; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:4.0gd; mso-para-margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; mso-pagination:none; font-size:10.5pt; mso-bidi-font-size:12.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-font-kerning:1.0pt; mso-fareast-language:ZH-CN;} p.MsoToc4, li.MsoToc4, div.MsoToc4 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:63.0pt; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:6.0gd; mso-para-margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoToc5, li.MsoToc5, div.MsoToc5 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:84.0pt; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:8.0gd; mso-para-margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoToc6, li.MsoToc6, div.MsoToc6 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:105.0pt; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:10.0gd; mso-para-margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoToc7, li.MsoToc7, div.MsoToc7 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:126.0pt; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:12.0gd; mso-para-margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoToc8, li.MsoToc8, div.MsoToc8 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:147.0pt; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:14.0gd; mso-para-margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoToc9, li.MsoToc9, div.MsoToc9 {mso-style-update:auto; mso-style-noshow:yes; mso-style-unhide:no; mso-style-next:Normal; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:168.0pt; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:16.0gd; mso-para-margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoFootnoteText, li.MsoFootnoteText, div.MsoFootnoteText {mso-style-noshow:yes; mso-style-unhide:no; mso-style-link:"Footnote Text Char"; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; line-height:12.0pt; mso-pagination:none; mso-layout-grid-align:none; text-autospace:none; font-size:7.5pt; mso-bidi-font-size:10.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN; mso-bidi-language:HE;} p.MsoHeader, li.MsoHeader, div.MsoHeader {mso-style-unhide:no; mso-style-link:"Header Char"; margin:0mm; margin-bottom:.0001pt; text-align:center; text-indent:21.25pt; line-height:12.0pt; mso-pagination:none; tab-stops:center 207.65pt right 415.3pt; layout-grid-mode:char; mso-layout-grid-align:none; border:none; mso-border-bottom-alt:solid windowtext .75pt; padding:0mm; mso-padding-alt:0mm 0mm 1.0pt 0mm; font-size:9.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.MsoFooter, li.MsoFooter, div.MsoFooter {mso-style-unhide:no; mso-style-link:"Footer Char"; margin:0mm; margin-bottom:.0001pt; text-indent:21.25pt; line-height:12.0pt; mso-pagination:none; tab-stops:center 207.65pt right 415.3pt; layout-grid-mode:char; mso-layout-grid-align:none; font-size:9.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} span.MsoFootnoteReference {mso-style-noshow:yes; mso-style-unhide:no; vertical-align:super;} span.Heading1Char {mso-style-name:"Heading 1 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 1"; mso-ansi-font-size:20.0pt; mso-bidi-font-size:10.5pt; font-family:方正美黑簡體; mso-ascii-font-family:方正美黑簡體; mso-fareast-font-family:方正美黑簡體; mso-font-kerning:22.0pt; mso-fareast-language:ZH-CN;} span.Heading2Char {mso-style-name:"Heading 2 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 2"; mso-ansi-font-size:16.0pt; mso-bidi-font-size:15.0pt; font-family:方正楷體簡體; mso-fareast-font-family:方正楷體簡體; mso-fareast-language:ZH-CN;} span.Heading3Char {mso-style-name:"Heading 3 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 3"; mso-ansi-font-size:13.0pt; mso-bidi-font-size:10.5pt; font-family:"Arial","sans-serif"; mso-ascii-font-family:Arial; mso-fareast-font-family:SimHei; mso-hansi-font-family:Arial; mso-bidi-font-family:Arial; mso-fareast-language:ZH-CN;} span.Heading4Char {mso-style-name:"Heading 4 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 4"; mso-ansi-font-size:10.5pt; mso-fareast-language:ZH-CN; font-weight:bold;} span.Heading5Char {mso-style-name:"Heading 5 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 5"; mso-ansi-font-size:14.0pt; mso-bidi-font-size:14.0pt; mso-fareast-language:ZH-CN; font-weight:bold;} span.Heading6Char {mso-style-name:"Heading 6 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 6"; mso-ansi-font-size:10.5pt; mso-bidi-font-size:10.5pt; font-family:SimHei; mso-fareast-font-family:SimHei; mso-fareast-language:ZH-CN;} span.Heading7Char {mso-style-name:"Heading 7 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 7"; mso-ansi-font-size:10.5pt; mso-fareast-language:ZH-CN; font-weight:bold; mso-bidi-font-weight:normal;} span.Heading8Char {mso-style-name:"Heading 8 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 8"; mso-ansi-font-size:10.5pt; font-family:"Arial","sans-serif"; mso-ascii-font-family:Arial; mso-fareast-font-family:SimHei; mso-hansi-font-family:Arial; mso-fareast-language:ZH-CN;} span.Heading9Char {mso-style-name:"Heading 9 Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Heading 9"; mso-ansi-font-size:10.5pt; mso-fareast-language:ZH-CN;} p.a, li.a, div.a {mso-style-name:圖題; mso-style-unhide:no; margin-top:3.6pt; margin-right:0mm; margin-bottom:9.6pt; margin-left:0mm; mso-para-margin-top:.3gd; mso-para-margin-right:0mm; mso-para-margin-bottom:.8gd; mso-para-margin-left:0mm; text-align:center; line-height:15.5pt; mso-pagination:none; mso-outline-level:6; font-size:9.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-font-kerning:1.0pt; mso-fareast-language:ZH-CN;} p.3, li.3, div.3 {mso-style-name:标題3; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.0pt; mso-char-indent-count:2.0; line-height:15.6pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:方正大标宋簡體; mso-hansi-font-family:"Times New Roman"; mso-bidi-font-family:"Times New Roman"; mso-fareast-language:ZH-CN;} p.4, li.4, div.4 {mso-style-name:标題4; mso-style-unhide:no; margin-top:6.0pt; margin-right:0mm; margin-bottom:6.0pt; margin-left:0mm; mso-para-margin-top:.5gd; mso-para-margin-right:0mm; mso-para-margin-bottom:.5gd; mso-para-margin-left:0mm; text-align:justify; text-justify:inter-ideograph; line-height:15.5pt; mso-pagination:none; mso-outline-level:4; mso-layout-grid-align:none; font-size:12.0pt; mso-bidi-font-size:10.5pt; font-family:方正大标宋簡體; mso-hansi-font-family:Arial; mso-bidi-font-family:Arial; mso-fareast-language:ZH-CN; mso-bidi-font-weight:bold;} p.5, li.5, div.5 {mso-style-name:标題5; mso-style-unhide:no; margin-top:6.0pt; margin-right:0mm; margin-bottom:6.0pt; margin-left:0mm; mso-para-margin-top:.5gd; mso-para-margin-right:0mm; mso-para-margin-bottom:.5gd; mso-para-margin-left:0mm; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.6pt; mso-pagination:none; mso-layout-grid-align:none; font-size:14.0pt; mso-bidi-font-size:10.5pt; font-family:"Arial","sans-serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.a0, li.a0, div.a0 {mso-style-name:圖; mso-style-unhide:no; margin-top:9.6pt; margin-right:0mm; margin-bottom:0mm; margin-left:0mm; margin-bottom:.0001pt; mso-para-margin-top:.8gd; mso-para-margin-right:0mm; mso-para-margin-bottom:0mm; mso-para-margin-left:0mm; mso-para-margin-bottom:.0001pt; text-align:center; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.a1, li.a1, div.a1 {mso-style-name:頂格小五; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:14.0pt; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.a2, li.a2, div.a2 {mso-style-name:表欄名; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:center; line-height:14.0pt; mso-pagination:none; layout-grid-mode:char; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:"Arial","sans-serif"; mso-fareast-font-family:SimHei; mso-bidi-font-family:"Times New Roman"; mso-fareast-language:ZH-CN;} p.a3, li.a3, div.a3 {mso-style-name:表文; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; line-height:14.0pt; mso-pagination:none; layout-grid-mode:char; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.a4, li.a4, div.a4 {mso-style-name:表題; mso-style-unhide:no; margin-top:6.0pt; margin-right:0mm; margin-bottom:3.0pt; margin-left:0mm; text-align:center; line-height:15.5pt; mso-pagination:lines-together; page-break-after:avoid; mso-outline-level:7; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:"Arial","sans-serif"; mso-fareast-font-family:SimHei; mso-font-kerning:22.0pt; mso-fareast-language:ZH-CN;} p.1, li.1, div.1 {mso-style-name:程式1; mso-style-unhide:no; margin-top:6.0pt; margin-right:0mm; margin-bottom:6.0pt; margin-left:0mm; mso-para-margin-top:.5gd; mso-para-margin-right:0mm; mso-para-margin-bottom:.5gd; mso-para-margin-left:0mm; text-align:justify; text-justify:inter-ideograph; text-indent:18.0pt; mso-char-indent-count:2.0; line-height:15.6pt; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:"Courier New"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.2, li.2, div.2 {mso-style-name:程式2; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:18.0pt; mso-char-indent-count:2.0; line-height:14.0pt; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:"Courier New"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.a5, li.a5, div.a5 {mso-style-name:程式代碼; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:14.0pt; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:"Courier New"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.a6, li.a6, div.a6 {mso-style-name:程式; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:12.0pt; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:SimHei; mso-hansi-font-family:SimSun; mso-bidi-font-family:"Times New Roman"; mso-fareast-language:ZH-CN;} p.a7, li.a7, div.a7 {mso-style-name:項目; mso-style-update:auto; mso-style-unhide:no; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:21.0pt; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:-21.0pt; line-height:15.5pt; mso-pagination:none; tab-stops:list 21.0pt; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.20, li.20, div.20 {mso-style-name:項目2; mso-style-unhide:no; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:42.25pt; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:-21.0pt; line-height:15.5pt; mso-pagination:none; tab-stops:list 42.25pt; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.a8, li.a8, div.a8 {mso-style-name:注; mso-style-update:auto; mso-style-unhide:no; margin-top:.3pt; margin-right:0mm; margin-bottom:.3pt; margin-left:0mm; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:FangSong_GB2312; mso-fareast-language:ZH-CN; mso-bidi-font-weight:bold;} p.a9, li.a9, div.a9 {mso-style-name:項目符号; mso-style-unhide:no; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:42.0pt; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:-21.0pt; line-height:15.5pt; mso-pagination:none; mso-list:l3 level1 lfo6; tab-stops:list 42.0pt; mso-layout-grid-align:none; font-size:10.5pt; mso-bidi-font-size:10.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.aa, li.aa, div.aa {mso-style-name:項目圓; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN; mso-bidi-font-weight:bold;} p.ab, li.ab, div.ab {mso-style-name:注意内容; mso-style-unhide:no; margin-top:6.0pt; margin-right:0mm; margin-bottom:6.0pt; margin-left:29.75pt; mso-para-margin-top:.5gd; mso-para-margin-right:0mm; mso-para-margin-bottom:.5gd; mso-para-margin-left:29.75pt; text-align:justify; text-justify:inter-ideograph; text-indent:-29.75pt; line-height:15.5pt; mso-pagination:none; layout-grid-mode:char; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:方正楷體簡體; mso-fareast-language:ZH-CN; mso-bidi-font-weight:bold;} span.FootnoteTextChar {mso-style-name:"Footnote Text Char"; mso-style-noshow:yes; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:"Footnote Text"; mso-ansi-font-size:7.5pt; mso-fareast-language:ZH-CN; mso-bidi-language:HE;} span.HeaderChar {mso-style-name:"Header Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:Header; mso-ansi-font-size:9.0pt; mso-bidi-font-size:9.0pt; mso-fareast-language:ZH-CN;} span.FooterChar {mso-style-name:"Footer Char"; mso-style-unhide:no; mso-style-locked:yes; mso-style-link:Footer; mso-ansi-font-size:9.0pt; mso-bidi-font-size:9.0pt; mso-fareast-language:ZH-CN;} p.ac, li.ac, div.ac {mso-style-name:提示; mso-style-unhide:no; margin-top:9.6pt; margin-right:0mm; margin-bottom:9.6pt; margin-left:31.2pt; mso-para-margin-top:.8gd; mso-para-margin-right:0mm; mso-para-margin-bottom:.8gd; mso-para-margin-left:31.2pt; text-align:justify; text-justify:inter-ideograph; text-indent:-31.2pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:方正楷體簡體; color:black; mso-fareast-language:ZH-CN;} p.ad, li.ad, div.ad {mso-style-name:頂格正文; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Arial","sans-serif"; mso-fareast-font-family:SimHei; mso-fareast-language:ZH-CN;} p.ae, li.ae, div.ae {mso-style-name:程式單; mso-style-unhide:no; mso-style-parent:程式; margin-top:6.0pt; margin-right:0mm; margin-bottom:6.0pt; margin-left:0mm; mso-para-margin-top:.5gd; mso-para-margin-right:0mm; mso-para-margin-bottom:.5gd; mso-para-margin-left:0mm; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:12.0pt; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:SimHei; mso-hansi-font-family:SimSun; mso-bidi-font-family:"Times New Roman"; mso-fareast-language:ZH-CN;} p.af, li.af, div.af {mso-style-name:懸挂; mso-style-unhide:no; margin-top:0mm; margin-right:0mm; margin-bottom:0mm; margin-left:104.3pt; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:-83.05pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} span.1Char {mso-style-name:"标題 1 Char"; mso-style-unhide:no; mso-ansi-font-size:18.0pt; mso-bidi-font-size:10.0pt; font-family:方正大标宋簡體; mso-ascii-font-family:方正大标宋簡體; mso-fareast-font-family:方正大标宋簡體; mso-hansi-font-family:Impact; mso-bidi-font-family:Arial;} p.af0, li.af0, div.af0 {mso-style-name:程式固定; mso-style-unhide:no; mso-style-parent:程式; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:8.0pt; mso-line-height-rule:exactly; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:SimHei; mso-hansi-font-family:SimSun; mso-bidi-font-family:"Times New Roman"; mso-fareast-language:ZH-CN;} p.af1, li.af1, div.af1 {mso-style-name:續表; mso-style-unhide:no; margin-top:0mm; margin-right:20.7pt; margin-bottom:0mm; margin-left:0mm; margin-bottom:.0001pt; mso-para-margin-top:0mm; mso-para-margin-right:1.97gd; mso-para-margin-bottom:0mm; mso-para-margin-left:0mm; mso-para-margin-bottom:.0001pt; text-align:right; text-indent:21.25pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; mso-bidi-font-size:10.5pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} p.af2, li.af2, div.af2 {mso-style-name:正文文; mso-style-unhide:no; margin:0mm; margin-bottom:.0001pt; text-align:justify; text-justify:inter-ideograph; text-indent:21.0pt; line-height:15.5pt; mso-pagination:none; mso-layout-grid-align:none; font-size:10.5pt; mso-bidi-font-size:9.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; color:black; mso-fareast-language:ZH-CN;} p.af3, li.af3, div.af3 {mso-style-name:單行頂格小五; mso-style-unhide:no; mso-style-parent:頂格小五; margin-top:6.0pt; margin-right:0mm; margin-bottom:6.0pt; margin-left:0mm; mso-para-margin-top:.5gd; mso-para-margin-right:0mm; mso-para-margin-bottom:.5gd; mso-para-margin-left:0mm; text-align:justify; text-justify:inter-ideograph; text-indent:21.25pt; line-height:14.0pt; mso-pagination:none; mso-layout-grid-align:none; font-size:9.0pt; font-family:"Times New Roman","serif"; mso-fareast-font-family:SimSun; mso-fareast-language:ZH-CN;} .MsoChpDefault {mso-style-type:export-only; mso-default-props:yes; font-size:10.0pt; mso-ansi-font-size:10.0pt; mso-bidi-font-size:10.0pt; mso-ascii-font-family:"Times New Roman"; mso-fareast-font-family:SimSun; mso-hansi-font-family:"Times New Roman"; mso-font-kerning:0pt;} @page {mso-page-border-surround-header:no; mso-page-border-surround-footer:no;} @page Section1 {size:210.0mm 842.0pt; margin:119.05pt 30.0mm 40.0mm 30.0mm; mso-header-margin:93.55pt; mso-footer-margin:110.55pt; mso-page-numbers:2; mso-paper-source:1;} div.Section1 {page:Section1;} @list l0 {mso-list-id:-5; mso-list-template-ids:-1;} @list l0:level1 {mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l0:level2 {mso-level-text:"%1/.%2"; mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l0:level3 {mso-level-text:"%1/.%2/.%3"; mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l0:level4 {mso-level-text:"%1/.%2/.%3/.%4"; mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l0:level5 {mso-level-text:"%1/.%2/.%3/.%4/.%5"; mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l0:level6 {mso-level-text:"%1/.%2/.%3/.%4/.%5/.%6"; mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l0:level7 {mso-level-text:"%1/.%2/.%3/.%4/.%5/.%6/.%7"; mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l0:level8 {mso-level-text:"%1/.%2/.%3/.%4/.%5/.%6/.%7/.%8"; mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l0:level9 {mso-level-style-link:"Heading 9"; mso-level-text:"%1/.%2/.%3/.%4/.%5/.%6/.%7/.%8/.%9"; mso-level-tab-stop:none; mso-level-number-position:left; mso-level-legacy:yes; mso-level-legacy-indent:0mm; mso-level-legacy-space:7.2pt; margin-left:0mm; text-indent:0mm;} @list l1 {mso-list-id:-2; mso-list-type:simple; mso-list-template-ids:-1760810702;} @list l1:level1 {mso-level-number-format:bullet; mso-level-text:; mso-level-tab-stop:21.0pt; mso-level-number-position:left; margin-left:21.0pt; text-indent:-21.0pt; mso-ansi-font-size:9.0pt; font-family:Wingdings;} @list l2 {mso-list-id:403643587; mso-list-type:hybrid; mso-list-template-ids:-1101624838 -483222822 67698691 67698693 67698689 67698691 67698693 67698689 67698691 67698693;} @list l2:level1 {mso-level-number-format:bullet; mso-level-text:; mso-level-tab-stop:42.25pt; mso-level-number-position:left; margin-left:42.25pt; text-indent:-21.0pt; font-family:Wingdings;} @list l3 {mso-list-id:1458571475; mso-list-type:hybrid; mso-list-template-ids:-465254064 -48204314 1214549418 67698693 67698689 67698691 67698693 67698689 67698691 67698693;} @list l3:level1 {mso-level-number-format:bullet; mso-level-style-link:項目符号; mso-level-text:; mso-level-tab-stop:42.0pt; mso-level-number-position:left; margin-left:42.0pt; text-indent:-21.0pt; mso-ansi-font-size:9.0pt; font-family:Wingdings;} @list l3:level2 {mso-level-number-format:bullet; mso-level-text:; mso-level-tab-stop:42.25pt; mso-level-number-position:left; margin-left:42.25pt; text-indent:-21.25pt; font-family:Wingdings;} @list l4 {mso-list-id:1617718560; mso-list-template-ids:-57006330;} @list l4:level1 {mso-level-text:%1; mso-level-tab-stop:21.6pt; mso-level-number-position:left; margin-left:21.6pt; text-indent:-21.6pt;} @list l4:level2 {mso-level-text:"%1/.%2"; mso-level-tab-stop:28.8pt; mso-level-number-position:left; margin-left:28.8pt; text-indent:-28.8pt;} @list l4:level3 {mso-level-text:"%1/.%2/.%3"; mso-level-tab-stop:36.0pt; mso-level-number-position:left; margin-left:36.0pt; text-indent:-36.0pt;} @list l4:level4 {mso-level-text:"%1/.%2/.%3/.%4"; mso-level-tab-stop:43.2pt; mso-level-number-position:left; margin-left:43.2pt; text-indent:-43.2pt;} @list l4:level5 {mso-level-text:"%1/.%2/.%3/.%4/.%5"; mso-level-tab-stop:50.4pt; mso-level-number-position:left; margin-left:50.4pt; text-indent:-50.4pt;} @list l4:level6 {mso-level-text:"%1/.%2/.%3/.%4/.%5/.%6"; mso-level-tab-stop:57.6pt; mso-level-number-position:left; margin-left:57.6pt; text-indent:-57.6pt;} @list l4:level7 {mso-level-style-link:"Heading 7"; mso-level-text:"%1/.%2/.%3/.%4/.%5/.%6/.%7"; mso-level-tab-stop:64.8pt; mso-level-number-position:left; margin-left:64.8pt; text-indent:-64.8pt;} @list l4:level8 {mso-level-style-link:"Heading 8"; mso-level-text:"%1/.%2/.%3/.%4/.%5/.%6/.%7/.%8"; mso-level-tab-stop:72.0pt; mso-level-number-position:left; margin-left:72.0pt; text-indent:-72.0pt;} @list l4:level9 {mso-level-text:"%1/.%2/.%3/.%4/.%5/.%6/.%7/.%8/.%9"; mso-level-tab-stop:79.2pt; mso-level-number-position:left; margin-left:79.2pt; text-indent:-79.2pt;} @list l5 {mso-list-id:1982736063; mso-list-template-ids:665075544;} @list l5:level1 {mso-level-suffix:space; mso-level-text:"%1/) "; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:31.2pt; text-indent:-31.2pt;} @list l5:level2 {mso-level-number-format:alpha-upper; mso-level-suffix:none; mso-level-text:"%2/. "; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:39.7pt; text-indent:-10.0mm;} @list l5:level3 {mso-level-suffix:none; mso-level-text:"%3/. "; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:51.05pt; text-indent:-10.0mm;} @list l5:level4 {mso-level-number-format:alpha-lower; mso-level-suffix:none; mso-level-text:"%4/. "; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:62.35pt; text-indent:-10.0mm;} @list l5:level5 {mso-level-number-format:none; mso-level-style-link:"Heading 5"; mso-level-suffix:none; mso-level-text:""; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:0mm; text-indent:0mm;} @list l5:level6 {mso-level-number-format:none; mso-level-suffix:none; mso-level-text:""; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:0mm; text-indent:0mm;} @list l5:level7 {mso-level-number-format:none; mso-level-suffix:none; mso-level-text:""; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:0mm; text-indent:0mm;} @list l5:level8 {mso-level-number-format:none; mso-level-suffix:none; mso-level-text:""; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:0mm; text-indent:0mm;} @list l5:level9 {mso-level-number-format:none; mso-level-suffix:none; mso-level-text:""; mso-level-tab-stop:none; mso-level-number-position:left; margin-left:0mm; text-indent:0mm;} ol {margin-bottom:0mm;} ul {margin-bottom:0mm;} -->
對諸如 PowerBuilder (後文簡寫為 PB )、 Visual Basic 和 Dephi 等大多數可視化程式設計語言來講,程式設計的核心是對象的事件、屬性和方法,但對 Windows 系統本身而言,卻是以消息處理為其控制機制。 Windows 把系統中的對象都作為視窗來對待,每個視窗都有一個用來辨別其身份的句柄。 Windows 通過向視窗發送消息,在開發語言中轉化為對象的事件,然後驅動對象,響應使用者的動作。在許多面向對象的可視化程式設計語言中, Windows 的衆多消息已經演變成了對象的屬性或方法。本章内容包括 Windows 系統的消息機制、消息的發送、消息的應用執行個體等。
1.1 Windows 的工作機制
1.1.1 Windows 的工作方式 —— 視窗、事件和消息
全面地讨論 Windows 的内部工作機制需要很大的篇幅,對于一般的 PB 使用者當然沒有必要深入了解所有的技術細節。 Windows 系統的工作機制,簡單地說就是 3 個關鍵的概念:視窗、事件和消息。
不妨簡單地将視窗看做帶有邊界的矩形區域。讀者也許已經了解多種不同類型的視窗,如 Windows 系統的“資料總管”視窗、文字處理程式中的文檔視窗或者彈出提示有約會資訊的消息對話框視窗等。除了這些最普通的視窗外,實際上還有許多其他類型的視窗。指令按鈕是一個視窗,圖示、文本框、選項按鈕和菜單條也都是視窗。
Windows 作業系統通過給每一個視窗指定一個惟一的辨別号(視窗句柄,常用 hWnd 表示)來管理所有的視窗。作業系統連續地監視每一個視窗的活動或事件的信号。事件可以通過諸如單擊滑鼠或按下按鍵的操作而産生,也可以通過程式的控制而産生,甚至可以由另一個視窗的操作而産生。
每發生一次事件,将引發一條消息發送至作業系統。作業系統處理該消息并廣播給其他視窗。然後,每一個視窗才能根據自身處理該條消息的指令而采取适當的操作(例如,當視窗解除了其他視窗的覆寫時,重新繪制自身視窗)。
可以想象,處理各種視窗、事件和消息的所有可能的組合将有驚人的工作量。幸運的是, PB 使使用者擺脫了所有的低層消息處理。許多消息由 PB 自動處理了,其他的作為事件過程由程式設計者自行處理,這樣可以快速建立強大的應用程式,而毋需涉及不必要的細節。
1.1.2 句柄的概念
在解釋消息之前,首先了解系統如何準确地将消息發送到指定的視窗。當一個應用或多個應用運作後,會同時建立許多個視窗, Windows 作為系統的“大總管”,那麼它又是如何識别每一個視窗呢?在程式設計時,通過視窗的名稱屬性,為每個視窗命名,然後在程式其他部分把視窗名作為識别視窗的辨別。這種通過為視窗命名來識别不同視窗的方法,對 Windows 系統來講顯然是不現實的。 Windows 系統是通過稱之為句柄的辨別符來識别每一個視窗。
句柄是系統動态配置設定給視窗的 32 位整型數辨別值,常用 hWnd 表示,即英文 handle to a window 的縮寫。大量 API 函數都需要視窗句柄作參數,或傳回一個視窗或裝置場境的句柄。句柄可以通俗地了解為 Windows 為系統中所有存在的視窗動态配置設定的身份識别号碼。
在 PB 中,可以通過 handle 函數來取得視窗和控件的句柄,當聲明 API 函數時,常把儲存句柄的變量聲明為 Long 或 Ulong 長整型資料類型。 Windows 為視窗和控件配置設定句柄辨別是動态,同樣的程式每次運作時和在不同計算機上運作時所配置設定的視窗句柄辨別可能是完全不一樣的。
視窗的句柄屬性僅能在運作時通路,該屬性對視窗的外觀并沒有任何影響,它僅作為 API 函數調用的參數或傳回值,或其他需識别視窗或對象的地方。在後面章節中,讀者将會看到幾乎所有涉及視窗的 API 函數都需要傳遞 hWnd 參數,以便函數準确獲得使用者要處理的視窗或對象。
句柄作為由作業系統定義的惟一的長整型值,可以用它來引用窗體和控件等對象。在 Windows 系統中, API 函數的調用常用的句柄包括視窗句柄,菜單句柄、裝置對象句柄、裝置場景句柄,等等。如果函數需要用句柄作為參數,則應該把參數聲明為傳值,對于傳回句柄的 API 函數,應将傳回的句柄值聲明為 Long 或 Ulong 類型資料類型。句柄是一種辨別符( ID )編号,而不是指針或者數值,不要試圖對它們進行任何數學運算。
1.1.3 消息的概念
Windows 系統是以消息處理為其控制機制,系統通過消息為視窗過程( windows procedure )傳遞輸入。系統和應用兩者都可以産生消息。對于每個輸入事件,例如使用者按下了鍵盤上的某個鍵、移動了滑鼠、單擊了一個控件上的滾動條,等等,系統都将産生一系列消息。此外,對于應用帶給系統的變化,如字型資源的改變、應用本身視窗的改變,系統都将通過消息以響應這種變化。應用通過産生消息訓示應用的視窗完成特定的任務,或與其他應用的視窗進行通信。
每個視窗都有一個處理 Windows 系統發送消息的處理程式,稱為視窗程式。它是隐含在視窗背後的一段程式腳本,其中包含對事件進行處理的代碼。
Windows 系統為每條消息指定了一個消息編号,例如當一個視窗變為活動視窗時,它事實上是收到一條來自 Windows 系統的 WM_ACTIVATE 消息,該消息的編号為 6 ,它對應于 PB 視窗的 Activate 事件。對于視窗來說,諸如 Open 、 Activate 、 MouseDown 、 Resize 等事件,實際上對應的是視窗内部的消息處理程式,這些程式對于使用者來講是不可見的。類似地,指令按鈕也有消息處理程式,它的處理程式響應諸如 WM_LBUTTONDOWN 和 WM_RBUTTONDOWN 之類的消息,即激活指令按鈕的 MouseDown 事件。
系統向視窗發送的消息通常包含 3 個參數,分别是:
( 1 )視窗句柄( a window handle ):視窗句柄用來辨別消息将要發送到的視窗對象,系統使用視窗句柄來确定哪一個視窗句柄應該接收該消息。
( 2 )消息辨別符( a message identifier ):消息辨別符是用來區分不同消息的命名常量,當視窗過程接收到一個消息時,它使用消息辨別符來确定如何處理該消息。例如,消息辨別符 WM_PAINT 告訴視窗過程“視窗的客戶區已經發生變化,視窗必須進行重新繪制”。
( 3 )消息參數( message parameters ):消息參數用來表述視窗過程處理消息時所使用的資料或資料的位置,通常用一對參數表示。消息參數的意義和取值取決于消息。消息參數取值可以是整型數、 Bit 位辨別、指向結構的指針,等等,當不需要使用消息參數時,通常将其設定為 NULL 。視窗過程必須通過檢查消息辨別符來确定如何對消息參數進行解釋。
有關消息辨別符、消息參數的具體使用,将在後面介紹 Sendmessage 函數時給予進一步 解釋。
1.1.4 消息的類型
1 .系統定義的消息
當系統與應用進行通信時,系統将發送或郵寄消息。系統通過這些消息控制應用的運作,并為應用的程序提供輸入或其他資訊。應用内部也可發送或郵寄系統定義的消息,應用通常使用這些消息控制由預先注冊的視窗類建立的視窗的操作。
每一個系統定義的消息都有一個惟一的消息辨別符(值),并用一個表明消息用途辨別符常量表示(這些在 SDK 的頭檔案中定義)。如 WM_PAINT 消息辨別符表示要求視窗進行重繪的消息。
消息辨別符常量字首表示消息所屬的消息類别,如 WM_ 表示視窗類消息, BM_ 表示按鈕類消息,表 1-1 給出了不同類别消息的字首。
在 PB 中, 消息辨別符常量通常聲明為視窗或對象的執行個體常量,例如:
CONSTANT long WM_MOUSEMOVE = 512
CONSTANT long WM_LBUTTONDOWN = 513
CONSTANT long WM_LBUTTONUP = 514
CONSTANT long WM_LBUTTONDBLCLK = 515
CONSTANT long WM_RBUTTONDOWN = 516
CONSTANT long WM_RBUTTONUP = 517
CONSTANT long WM_RBUTTONDBLCLK = 518
表 1-1 Windows 系統定義的消息類别
消息辨別符字首 | 消息分類 |
ABM | 應用桌面工具欄消息 |
BM | 按鈕控件消息 |
CB | 組合框控件消息 |
CBEM | 擴充組合框控件消息 |
CDM | 通用對話框消息 |
DBT | 裝置消息 |
DL | 拖曳清單框控件消息 |
DM | 預設按鈕控件消息 |
DTM | 日期時間選取控件消息 |
續表
消息辨別符字首 | 消息分類 |
EM | 編輯控件消息 |
HDM | 頭控件消息 |
HKM | 熱鍵控件消息 |
IPM | IP 位址控件消息 |
LB | 清單框控件消息 |
LVM | 清單視圖控件消息 |
MCM | 月曆控件消息 |
PBM | 進度條控件消息 |
PGM | Pager 控件消息 |
PSM | 屬性頁面消息 |
RB | Rebar 控件消息 |
SB | 狀态欄視窗消息 |
SBM | 滾動條控件消息 |
STM | 靜态控件消息 |
TB | 工具欄消息 |
TBM | 跟蹤條控件消息 |
TCM | Tab 控件消息 |
TTM | Tooltip 控件消息 |
TVM | 樹形控件消息 |
UDM | Up-down 控件消息 |
WM | 普通視窗消息 |
Windows 系統使用了成千上萬條消息。從視窗到控件都有一組可接收和響應的消息。在 Visual Basic 的 API 浏覽器中,以常量的方式列出了 Windows 的大部分消息。
據粗略統計,微軟在 MSDN 中列出的消息約有數千種,全部弄清楚這麼多種消息是不現實的,也是沒有必要的。這是因為 PB 已經将很多消息封裝為了對象的“屬性”(例如視窗的 Title 和 WindowState 屬性)和“方法(函數)”(例如關閉視窗函數 Close )。可以發現,消息可能演變成 PB 對象的屬性、方法(函數)和事件。既然 PB 已經對消息進行了封裝,那麼又何必使用消息來進行程式設計呢?這時因為, PB 提供的事件、屬性和方法并未完全涵蓋所有消息,為了彌補 PB 在某些功能的不足,常使用系統消息或應用自定義的消息來強化 PB 的程式設計。
2 .應用定義的消息
應用也可以建立自己的消息,并将消息應用于它的視窗或與其他視窗的程序進行通信。如果應用建立了自己的消息,接收消息的視窗過程必須解釋消息,同時對消息進行恰當的處理。
系統保留的消息辨別符的取值範圍為 0x0000 ~ 0x03FF ( 0 ~ 1023 ),專門用于系統定義的消息;應用定義的消息不能使用這些值,應用定義的消息取值範圍為 0x0400 ~ 0x7FFF ( 0 ~ 32767 )。
RegisterWindowMessage 函數提供了配置設定消息編号的功能,該函數用一個消息名稱作為參數,并為這個名稱配置設定一個惟一的、尚未使用過的編号。
1.1.5 用于發送消息的 API 函數
Windows 應用程式允許應用程式向自己或其他應用程式發送消息,甚至可以向 Windows 作業系統本身發送消息(比如要求關閉作業系統或重新啟動作業系統)。 Windows 提供了 2 個專門 用于發送消息的 API 函數 SendMessage 和 PostMessage 。
1 . SendMessage 函數
SendMessage 函數發送指定的消息到視窗或 Windows 系統,然後函數調用視窗的處理消息的過程,并等待視窗過程處理完消息後傳回。
C 原型
LRESULT SendMessage (HWND hWnd, UINT wMsg, WPARAM wParam, LPARAM lParam );
PB 聲明
FUNCTION Long SendMessage (Long hwnd, Long wMsg, Long wParam, Long lParam) LIBRARY "user32.dll" ALIAS FOR "SendMessageA"
參 數
hWnd 為接收消息視窗的句柄;
wMsg 指定要發送的消息;
wParam 依賴于消息 wMsg 的其他資訊;
lParam 依賴于消息 wMsg 的其他資訊。
傳回值
函數傳回消息的處理結果,該值取決于消息的類型。
wParam 和 lParam 兩個參數的含義随消息 wMsg 參數不同而改變,是以每當向視窗傳遞某種消息時,除了要了解該消息的含義外,還要注意 wParam 和 lParam 的含義和設定。
SendMessage 函數會傳回一個 Long 值,由于這個函數是直接調用視窗程式,是以視窗程式可以傳回一個值,把它作為 SendMessage 函數的傳回值,這個傳回值的具體含義由消息決定。不過,除非在 MSDN 明确列出了該消息的傳回值,否則,傳回值就沒有具體意義,應該忽略。此外,在使用傳回值時,通常調用 SendMessageTimeOut 函數檢 查是否逾時,因為隻有在消息完全處理完畢後,才能得到一個有效傳回值。
前面曾提到預設的視窗過程函數 DefWindowProc 用來處理應用程式無法處理的消息,該函數確定所有消息都要處理,無論這些消息是否對視窗有用。調用 DefWindowProc 函數時,需要傳入與視窗消息處理過程相同的參數。
C 原型
LRESULT DefWindowProc ( HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam );
PB 聲明
FUNCTION Long DefWindowProc (Long hwnd,Long wMsg,Long wParam,Long lParam) LIBRARY "user32.dll" ALIAS FOR "DefWindowProcA"
參 數
hWnd 視窗句柄;
wMsg 指定要發送的消息;
wParam 依賴于消息 wMsg 的其他資訊;
lParam 依賴于消息 wMsg 的其他資訊。
傳回值
函數傳回消息的處理結果,該取決于消息的類型。
2. PostMessage 函數
PostMessage 函數同 SendMessage 類似,它把消息放在指定視窗建立的線程的消息隊列中,然後不等消息處理完就傳回,而不像 SendMessage 那樣必須等到消息處理完畢才傳回。目标視窗通過 GetMessage 或 PeekMessage 從消息隊列中取出并處理。
C 原型
LRESULT PostMessage ( HWND hWnd , UINT Msg , WPARAM wParam , LPARAM lParam );
PB 聲明
FUNCTION Long PostMessage (Long hwnd,Long wMsg,Long wParam,Long lParam) LIBRARY "user32.dll" ALIAS FOR " PostMessageA"
參 數
hWnd 為接收消息視窗的句柄;
Msg 指定要發送的消息;
wParam 依賴于消息 Msg 的其他資訊;
lParam 依賴于消息 Msg 的其他資訊。
傳回值
如果函數調用成功,函數傳回值為非 0 ;如果調用失敗,函數傳回 0 。
示 例
下面代碼示範了如何通過發送消息,在 PB 應用中關閉另外運作的第三方程式。
( 1 )運作 Windows 的系統的記事本程式 NotePad ,并建立一個未命名的文檔。
( 2 )在 PB 中建立一個視窗,為視窗聲明如下對象級外部函數和執行個體變量:
FUNCTION Long FindWindow(String lpClassName, String lpWindowName) LIBRARY "user32.dll" ALIAS FOR "FindWindowA"
FUNCTION Long PostMessage(Long hwnd, Long wMsg, Long wParam, Long lParam) LIBRARY "user32.dll" ALIAS FOR "PostMessageA"
Constant long WM_QUIT = 18
( 3 )在視窗上放置一個按鈕控件,為按鈕的 Clicked 事件加入如下腳本:
String ls_sTitle, pbNullString
Long ll_iHwnd, ll_ihTask
Long ll_iReturn
SetNull(pbNullString)
ls_sTitle = " 未定标題 – 記事本 "
ll_iHwnd = FindWindow(SetNull, ls_sTitle)
ll_iReturn = PostMessage(ll_iHwnd, WM_QUIT, 0, 0)
MessageBox(" 提示資訊 "," 記事本已經關閉! ")
上述代碼運作後,使用 FindWindow 函數擷取 Windows 記事本程式視窗的句柄,然後向記事本視窗發送 WM_QUIT 消息,記事本程式将被關閉。
1.2 事件與消息
1.2.1 從消息到事件
雖然在前面提到 Windows 系統會産生事件來驅動對象,但更嚴格的講 Windows 先産生消息,然後由 PB 将其轉化為驅動對象的事件。那麼 PB 是如何将消息轉換為事件呢?
1.1 節介紹了消息的概念。也可以通俗地将消息了解為由 Windows 作業系統送往程式的事件。它是系統中各個控件(視窗)溝通的方式。舉例來說,當移動滑鼠、按下滑鼠鍵、改變視窗視窗大小時, Windows 都會送出消息以通知程式。當然,為了要辨識事件的内容, Windows 系統中預定義了許多的消息,如 WM_PAINT , WM_CHAR 等。
當事件發生時, Windows 系統根據視窗的身份碼——句柄 hWnd ,判斷該事件必須由哪個視窗接收,然後将事件以消息的方式送往程式的視窗中。雖然在 Windows 系統中包含了數以百計的事件,但是作業系統并沒有為各個事件設計不同的消息結構,而是以一個一般性的結構來描述消息,
Windows 使用了一個特殊的函數來實作這一過程,這個函數的名稱叫做“視窗處理函數”或者叫做“視窗消息處理函數”,該函數就是 WindowProc 。
LRESULT CALLBACK WindowProc(HWND hwnd , UINT uMsg , WPARAM wParam , LPARAM lParam ) ;
從函數的定義可以看出,任何要發送的消息都有 4 個參數,其中:
HWND hwnd ——發送視窗的句柄
UINT uMsg ——消息代碼
Windows 中每一個消息都有惟一的一個代碼。在 Visual Basic 的 API 文本浏覽器中以常量的格式列出了所有消息名和代碼,在 PB 中也可以直接利用 Visual Basic 的 API 文本浏覽器列出的這些消息,惟一需要做的就是将 Visual Basic 十六進制消息代碼轉換為 PB 的十進制,如在 Visual Basic 聲明定義的有關滑鼠移動的消息:
Public Const WM_MOUSEMOVE = &H200
在 PB 中應聲明為:
Constant Long WM_MOUSEMOVE = 512
WPARAM wParam 和 LPARAM lParam 為兩個 32 位的長整型值,用來指定目前發送消息時所帶資訊,如在滑鼠移動時傳回滑鼠的位置等。
當 Windows 有消息需要通知程式的時候,它就會調用該函數,然後自己的程式就從中檢測發送的消息。 Windows 中消息的種類是很多的,不可能也沒有必要檢測所有的消息,隻需要檢測感興趣的消息即可。檢測消息的程式其實就是一個條件判斷組合,如圖 1.1 所示。
那麼未處理的消息到那裡去了? Windows 系統為視窗提供了預設的視窗過程 DefWindowProc ,這個視窗過程将負責處理那些不需要的消息。正因為有了這個預設視窗過程,才可以利用 Windows 的視窗進行開發,而不必過多關注視窗各種消息的處理。例如,視窗在被拖動時會有很多消息發送,可以不予理睬讓系統自己去處理。
圖 1.1 消息處理流程
從上面分析可以看出,事件驅動機制是針對諸如 PB 、 Visual Basic 這類面向對象的開發環境而言,在其背後隐含的是 Windows 系統的消息驅動機制,但 Windows 系統的消息驅動應用範圍要比進階開發語言定義的事件驅動範圍廣泛的多。
1.2.2 P B 事件對消息的封裝
在 PB 中,除了為視窗和控件預置的事件外, PB 還将 Windows 系統的許多消息封裝為使用者自選事件,根據與 Windows 系統的消息的對應關系,為每個事件定義了 EventID ,如圖 1.2 所示。
當視窗或控件的預置事件無法滿足程式設計要求時,可以使用這些自選事件。如在裝置場景中繪制的位圖,當視窗大小改變時,位圖并不會自動重繪。這時就需要使用視窗的事件 ID 号位 pbm_paint 事件,該事件與視窗的 WM_PAINT 消息相對應,當視窗發生變化時強迫視窗重繪。在 PB 中,事件 ID 的作用是把 PB 的事件與系統消息聯系起來,被使用者的動作或其他系統活動觸發的事件必須具有 ID 号。對于 PB 的系統對象,如視窗、按鈕等控件,定義好的系統事件通常都使用 ID 号。
當使用者使用自選事件時,可以使用如圖 1.2 所示列在 Event Declaration 對話框中的事件 ID 号,用來響應某個系統消息。如果定義被系統消息觸發的使用者自選事件,可以從 ID 号清單中選擇事件 ID 号。其中,列在 Event 對話框中的所有以 pbm_ 字首開始的 ID 号,為映射到 PB 中的系統消息。在定義使用者自選事件時,不能修改與事件 ID 号相關的參數及傳回值,因為這些是整個事件 ID 号的具體組成部分。如果與事件 ID 号相應的系統消息發生時, PB 觸發該事件,并為事件的參數指派。如果使用者自定義事件,并且與系統消息無關,則不為事件選擇 ID 号。這樣事件将不會被使用者的動作或系統的活動觸發,隻能在應用中用腳本來觸發。
圖 1.2 PB 的使用者自選事件
由于 PB 的技術開發文檔中并未列出每個事件 ID 的具體含義及與 Windows 系統消息的對應關系,使用者在使用這些自選事件時常常感到困惑。為此,筆者将這些事件與 Windows 系統的消息的對應關系及具體含義逐一進行了分析,這些 PB 的自選事件 ID 涵蓋了視窗消息,以及按鈕、組合框、清單框、編輯掩碼等控件的消息,下面逐一列在表 1-2 ~ 1-8 中,供讀者參考。
( 1 ) PB 的按鈕自選事件及對應的系統消息,如表 1-2 所示。
( 2 ) PB 的組合框控件( ComBox )自選事件及對應的系統消息,如表 1-3 所示。
表 1-2 按鈕事件及對應的系統消息
PB 的事件 ID | 對應的系統消息 | 消息作用 |
pbm_bmgetstate | BM_GETSTATE | 按鈕是否加亮 |
pbm_bmsetcheck | BM_SETCHECK | 設定按鈕的選中或未選中狀态 |
pbm_bmsetstate | BM_SETSTATE | 加亮或不加亮按鈕 |
pbm_bnclicked | BN_CLICKED | 按鈕控件被單擊 |
pbm_bndisable | BN_DISABLE | 使按鈕控件無效 |
pbm_bndoubleclicked | BN_DOUBLECLICKED | 按鈕控件被輕按兩下 |
pbm_bndragdrop | BN_DRAGDROP | 一個對象被放到按鈕控件 |
pbm_bndragenter | BN_DRAGENTER | 一個對象被拖到按鈕控件 |
pbm_bndragleave | BN_DRAGLEAVE | 一個對象被拖離按鈕控件 |
pbm_bndragover | BN_DRAGOVER | 一個對象被拖經按鈕控件 |
pbm_bnhilite | BN_HILITE | 按鈕控件被加亮 |
pbm_bnpaint | BN_PAINT | 按鈕控件被繪制 |
pbm_bnsetfocus | BN_SETFOCUS | 按鈕控件獲得焦點 |
pbm_bnunhilite | BN_UNHILITE | 按鈕控件不被加亮 |
表 1-3 組合框事件及對應的系統消息
PB 的事件 ID | 對應的系統消息 | 消息作用 |
pbm_cbaddstring | CB_ADDSTRING | 将字元串加到組合框 |
pbm_cbdeletestring | CB_DELETESTRING | 從組合框删除一個字元串 |
pbm_cbdir | CB_DIR | 加一個目錄清單到組合框 |
pbm_cbfindstring | CB_FINDSTRING | 搜尋以一組字元開頭的字元串 |
pbm_cbfindstringexact | CB_FINDSTRINGEXACT | 搜尋與所提供的字元完全比對的字元串 |
pbm_cbgetcount | CB_GETCOUNT | 清單框中的項數 |
pbm_cbgetcursel | CB_GETCURSEL | 目前被選項的數目 |
pbm_cbgetdroppedcontrolset | CB_GETDROPPEDCONTROLSET | 清單框在螢幕上的坐标位置 |
pbm_cbgeteditsel | CB_GETEDITSEL | 編輯器控件中被選字元的範圍 |
pbm_cbgetextendedui | CB_GETEXTENDEDUI | 預設或擴充的使用者界面 |
pbm_cbgetitemdata | CB_GETITEMDATA | 重畫的清單框中的 4 位元組( 32 位)項 |
pbm_cbgetitemheight | CB_GETITEMHEIGHT | 清單框中某一項的高度 |
pbm_cbgetlbtext | CB_GETLBTEXT | 清單框中的文本 |
pbm_cbgetlbtextlen | CB_GETLBTEXTLEN | 清單框中文本的長度 |
pbm_cbinsertstring | CB_INSERTSTRING | 向清單框中插入新的字元串項 |
pbm_cblimittext | CB_LIMITTEXT | 限制能被輸入到清單框中的字元數 |
pbm_cbresetcontent | CB_RESETCONTENT | 删除清單框中所有内容 |
pbm_cbselectstring | CB_SELECTSTRING | 搜尋比對的字元串并顯示 |
pbm_cbsetcursel | CB_SETCURSEL | 在清單框中選擇并顯示一項 |
pbm_cbseteditsel | CB_SETEDITSEL | 在清單框的編輯區域中選擇一塊文本 |
pbm_cbsetextendedui | CB_SETEXTENDEDUI | 設定預設或擴充的使用者界面 |
pbm_cbsetitemdata | CB_SETITEMDATA | 在清單框中設定 4 位元組( 32 位)項 |
pbm_cbsetitemheight | CB_SETITEMHEIGHT | 設定清單框中項的高度 |
pbm_cbshowdropdown | CB_SHOWDROPDOWN | 顯示或隐藏清單框中下拉清單區域 |
pbm_cbndblclk | CBN_DBLCLK | 使用者在清單中某一項上輕按兩下滑鼠 |
pbm_cbndragdrop | CBN_DRAGDROP | 一個對象被放到組合框控件上 |
pbm_cbndragenter | CBN_DRAGENTER | 一個對象被拖到組合框控件上 |
pbm_cbndragleave | CBN_DRAGLEAVE | 一個對象被拖離組合框控件 |
pbm_cbndragover | CBN_DRAGOVER | 一個對象被拖經組合框控件 |
pbm_cbndropdown | CBN_DROPDOWN | 清單框的下拉區域即将被顯示 |
pbm_cbneditchange | CBN_EDITCHANGE | 編輯器控件中的文本發生變化 |
pbm_cbneditupdate | CBN_EDITUPDATE | 清單框編輯器控件中的文本即将被改變 |
pbm_cbnerrspace | CBN_ERRSPACE | 清單框滿,不能再向其中加入項 |
pbm_cbnkillfocus | CBN_KILLFOCUS | 通用清單框失去焦點 |
pbm_cbnselchange | CBN_SELCHANGE | 清單框中被選文本被改變 |
pbm_cbnselendcancel | CBN_SELENDCANCEL | 使用者按下了“取消”按鈕 |
pbm_cbnselendok | CBN_SELENDOK | 使用者按下了“确認”按鈕 |
pbm_cbnsetfocus | CBN_SETFOCUS | 通用對話控件擁有焦點 |
( 3 ) PB 的編輯控件( EditMask )自選事件及對應的系統消息,如表 1-4 所示。
( 4 ) PB 的清單框控件( ListBox )自選事件及對應的系統消息,如表 1-5 所示。
表 1-4 編輯控件事件及對應的系統消息
PB 的自選事件 ID | 對應的系統消息 | 消息作用 |
pbm_emcanundo | EM_CANUNDO | 編輯器控件是否能撤消上一次修改 |
pbm_ememptyundobuffer | EM_EM_PTYUNDOBUFFER | 清空由 Windows 管理的取消操作的緩沖區 |
pbm_emfmtlines | EM_FMTLINES | 在多行編輯器控件的行尾增加或删除回車換行 |
pbm_emgetfirstvisibleline | EM_GETFIRSTVISIBLELINE | 傳回編輯器控件中可見的第一行的行号 |
pbm_emgethandle | EM_GETHANDLE | 獲得編輯器控件使用的記憶體句柄 |
pbm_emgetline | EM_GETLINE | 從編輯器控件中複制一行到記憶體緩沖區 |
pbm_emgetlinecount | EM_GETLINECOUNT | 傳回多行編輯器控件的行數 |
pbm_emgetmodify | EM_GETMODIFY | 文本是否被使用者修改 |
pbm_emgetrect | EM_GETRECT | 傳回控件的長方形域 |
pbm_emgetsel | EM_GETSEL | 傳回被選文本的起始位置 |
pbm_emlimittext | EM_LIMITTEXT | 限制使用者鍵入的文本長度 |
pbm_emlinefromchar | EM_LINEFROMCHAR | 傳回被選文本的行号 |
pbm_emlineindex | EM_LINEINDEX | 傳回控件中被選行第一個字元在編輯串中的位置 |
pbm_emlinelength | EM_LINELENGTH | 傳回編輯器控件中被選行中的字元數 |
pbm_emlinescroll | EM_LINESCROLL | 水準或垂直卷滾編輯器控件 |
pbm_emreplacesel | EM_REPLACESEL | 從剪貼闆或從鍵盤上用新文本替換被選文本 |
pbm_emsethandle | EM_SETHANDLE | 設定編輯器控件的句柄 |
pbm_emsetmodify | EM_SETMODIFY | 設定編輯器控件的 modified 标志 |
pbm_emsetpasswordchar | EM_SETPASSWORDCHAR | 設定使用者輸入任何文本時顯示的字元,在輸入密碼時的顯示 |
pbm_emsetrect | EM_SETRECT | 設定 / 重置編輯器控件所在的長方形區域 , 編輯器控件中的文本被重畫 |
pbm_emsetrectnp | EM_SETRECTNP | 除了不重畫文本,大緻與 setrect 相同 |
pbm_emsetsel | EM_SETSEL | 選擇字元 |
pbm_emsettabstops | EM_SETTABSTOPS | 在多行編輯器控件中設定 tabstops |
pbm_emsetwordbreak | EM_SETWORDBREAK | 設定新的詞拆分函數 |
pbm_emsetwordbreakproc | EM_SETWORDBREAKPROC | 設定新的詞拆分過程 |
pbm_emundo | EM_UNDO | 撤消最近的編輯操作 |
pbm_enchange | EN_CHANGE | 編輯器控件中的文本發生改變 |
pbm_enerrspace | EN_ERRSPACE | 編輯器控件記憶體緩沖區溢出 |
pbm_enhscroll | EN_HSCROLL | 使用者點中上水準滾動條 |
pbm_enmaxtext | EN_MAXTEXT | 使用者試圖輸入比允許更多的文本 |
pbm_enupdate | EN_UPDATE | 編輯器控件即将顯示使用者的修改 |
pbm_envscroll | EN_VSCROLL | 使用者點中垂直滾動條 |
表 1-5 清單框控件事件及對應的系統消息
PB 的事件 ID | 對應的系統消息 | 消息作用 |
pbm_lbaddstring | LB_ADDSTRING | 向清單框控件中增加一項或一個字元串 |
pbm_lbdeletestring | LB_DELETESTRING | 從清單框中删除一項或一個字元串 |
pbm_lbdir | LB_DIR | 用目錄清單填充清單框 |
pbm_lbfindstring | LB_FINDSTRING | 在清單框中搜尋與所給字元串比對的項 |
pbm_lbfindstringexact | LB_FINDSTRINGEXACT | 在清單框中搜尋與所給字元串精确比對的項 |
pbm_lbgetcaretindex | LB_GETCARETINDEX | 在清單框中搜尋擁有焦點的項 |
pbm_lbgetcount | LB_GETCOUNT | 确定清單框中的項數 |
pbm_lbgetcursel | LB_GETCURSEL | 确定所選項是第幾項 |
pbm_lbgethorizontalextent | LB_GETHORIZONTALEXTENT | 獲得清單框的寬度、計算水準卷滾 |
pbm_lbgetitemheight | LB_GETITEMHEIGHT | 确定清單框控件中項的高度 |
pbm_lbgetitemrect | LB_GETITEMRECT | 确定清單框的尺寸 |
pbm_lbgetsel | LB_GETSEL | 獲得清單框中目前所選的項 |
pbm_lbgetselcount | LB_GETSELCOUNT | 在多選清單框中獲得所選項的數目 |
pbm_lbgetselitems | LB_GETSELITEMS | 用清單框中各自的項号填充給定的整數數組 |
pbm_lbgettext | LB_GETTEXT | 獲得清單框中目前所選項的文本 |
pbm_lbgettextlen | LB_GETTEXTLEN | 獲得清單框中目前所選項的文本中的字元數 |
pbm_lbgettopindex | LB_GETTOPINDEX | 确定清單框中可見的最上面一項的項号 |
pbm_lbinsertstring | LB_INSERTSTRING | 向清單框中加入一個新字元串 |
pbm_lbresetcontent | LB_RESETCONTENT | 重置(消除)清單框中的内容 |
pbm_lbselectstring | LB_SELECTSTRING | 搜尋并加亮與所給字元比對的字元串 |
pbm_lbselitemrange | LB_SELITEMRANGE | 選擇 / 取消清單框中某一範圍中的項 |
pbm_lbsetcaretindex | LB_SETCARETINDEX | 設定清單框中的某一項擁有焦點 |
pbm_lbsetcolumnwidth | LB_SETCOLUMNWIDTH | 設定清單框中列的寬度 |
pbm_lbsetcursel | LB_SETCURSEL | 在清單框中選擇并加亮一項 |
pbm_lbsethorizontaltext | LB_SETHORIZONTALTEXT | 設定清單框中被水準卷滾的單元數 |
pbm_lbsetitemdata | LB_SETITEMDATA | 設定與清單框相關的 32 位 /4 位元組值 |
pbm_lbsetitemheight | LB_SETITEMHEIGHT | 設定清單框中項的高度 |
pbm_lbsetsel | LB_SETSEL | 在清單框中選擇一個字元串 |
pbm_lbsettabstops | LB_SETTABSTOPS | 設定清單框控件中 tabstops 的位置 |
pbm_lbsettopindex | LB_SETTOPINDEX | 滾動清單框使特定的項成為可見的最上面項 |
pbm_endblclk | LBN_DBLCLK | 使用者在清單框控件中的某一項上輕按兩下 |
pbm_enerrspace | LBN_ERRSPACE | 使用者試圖超越可在清單框中輸入字元的最大限制 |
pbm_enselcancel | LBN_SELCANCEL | 目前選取文本被取消 |
pbm_enselchange | LBN_SELCHANGE | 使用者在清單框中選擇或取消了一項 |
( 5 ) PB 的視窗自選事件及對應的系統消息,如表 1-6 所示。
表 1-6 視窗事件及對應的系統消息
PB 的事件 ID | 對應的系統消息 | 消息作用 |
pbm_activateapp | WM_ACTIVATEAPP | 被激活的視窗屬于另外一個應用 |
pbm_askcbformatname | WM_ASKCBFORMATNAME | 要求剪貼闆中的内容被複制到一個使用自定義格式的文本緩沖區中 |
pbm_char | WM_CHAR | 傳送鍵盤上按下的鍵 |
pbm_chartoitem | WM_CHARTOITEM | 通過轉換鍵盤來的字元,幫助清單框定位其中的項 |
pbm_childactivate | WM_CHILDACTIVATE | 一個子視窗被移動或激活 |
pbm_clear | WM_CLEAR | 使用者要删除目前編輯器控件中的内容 |
pbm_command | WM_COMMAND | 使用者選擇了一個菜單項、控件或使用了加速鍵 |
pbm_compacting | WM_COMPACTING | 系統記憶體資源不足;當 Windows 占用了多于 1/8 的 CPU 時間緊縮記憶體時,産生這條消息 |
pbm_compareitem | WM_COMPAREITEM | 當新項被加入清單框或組合框時産生此消息,系統用這條消息進行項之間的比較 |
pbm_ctlcolor | WM_CTLCOLOR | 一個控件即将被繪制,可在此時改變控件的顔色 |
pbm_deadchar | WM_DEADCHAR | 使用者選擇了一種非英語字元集或其他特殊字元集,這将改變下面将要輸入的字元 |
pbm_deleteitem | WM_DELETEITEM | 從清單框或組合框中移去一項 |
pbm_destroyclipboard | WM_DESTROYCLIPBOARD | 剪貼闆内容被清除 |
pbm_devmodechanged | WM_DEVMODECHANGED | WIN.INI 中的一個裝置名被修改 |
pbm_drawclipboard | WM_DRAWCLIPBOARD | 剪貼闆内容發生改變 |
pbm_drawitem | WM_DRAWITEM | 清單框或組合框的一項内容被改變 |
pbm_dropfiles | WM_DROPFILES | 當滑鼠左鍵在一個注冊為拖放檔案接受器的應用上釋放時,發出該消息 |
pbm_erasebkgnd | WM_ERASEBKGND | 視窗的客戶區需要重畫 |
pbm_fontchange | WM_FONTCHANGE | 應用可用的字型數改變 |
pbm_getdlgcode | WM_GETDLGCODE | 通知消息,說明目前使用哪種類型的鍵盤 |
pbm_getfont | WM_GETFONT | 擷取目前激活的字型 |
pbm_getminmaxinto | WM_GETMINMAXINTO | 檢索視窗可設定的最小或最大尺寸 |
pbm_gettext | WM_GETTEXT | 從一個控件 ( 如按鈕或編輯器控件 ) 中複制文本到一個記憶體緩沖區 |
pbm_gettextlength | WM_GETTEXTLENGTH | 用來确定一個控件中的字元數 |
pbm_hscrollclipboard | WM_HSCROLLCLIPBOARD | 剪貼闆的水準滾動條被使用 |
pbm_iconerasebkgnd | WM_ICONERASEBKGND | 一個最小化視窗需要重畫背景 |
pbm_initdialog | WM_INITDIALOG | 一個對話框即将被顯示 |
pbm_initmenu | WM_INITMENU | 一個菜單即将被顯示 |
pbm_initmenupopup | WM_INITMENUPOPUP | 一個彈出式視窗即将被顯示 |
pbm_keydown | WM_KEYDOWN | 鍵盤上的一個鍵被按下 |
續表
PB 的事件 ID | 對應的系統消息 | 消息作用 |
pbm_keyup | WM_KEYUP | 鍵盤上的一個鍵被釋放 |
pbm_mdiactive | WM_MDIACTIVE | 一個 MDI 子視窗(視窗)被激活 |
pbm_mdicascade | WM_MDICASCADE | 以重疊的形式重排所有的視窗 |
pbm_mdicreate | WM_MDICREATE | 建立一個視窗 |
pbm_mdidestroy | WM_MDIDESTROY | 從 MDI 架構中移去一個視窗 |
pbm_mdigetactive | WM_MDIGETACTIVE | 獲得目前活動的 MDI 視窗的句柄 |
pbm_mdiiconrange | WM_MDIICONRANGE | 在一個 MDI 架構中重排最小化視窗的圖示 |
pbm_mdimaximize | WM_MDIMAXIMIZE | 最大化一個 MDI 子視窗 |
pbm_mdinext | WM_MDINEXT | 激活下一個 MDI 子視窗(緊接着活動視窗的視窗) |
pbm_mdirestore | WM_MDIRESTORE | 把 MDI 視窗恢複到它原來的大小 |
pbm_mdisetmenu | WM_MDISETMENU | 将一個菜單與一個 MDI 視窗聯系起來 |
pbm_mdifitle | WM_MDIFITLE | 平鋪所有的 MDI 視窗 |
pbm_measureitem | WM_MEASUREITEM | 這個消息被送給即将建立的、内有按鈕或其他控件的視窗 |
pbm_menuchar | WM_MENUCHAR | 使用者使用了一個快捷鍵 , 但系統不支援該快捷鍵 |
pbm_menuselect | WM_MENUSELECT | 使用者選擇了一個菜單項 |
pbm_mouseactivate | WM_MOUSEACTIVATE | 使用者在一個非活動視窗中單擊了滑鼠 |
pbm_mousemove | WM_MOUSEMOVE | 使用者移動了滑鼠 |
pbm_ncactivate | WM_NCACTIVATE | 視窗的非客戶區即将被激活 |
pbm_nccalcsize | WM_NCCALCSIZE | 視窗的尺寸需要重新計算 |
pbm_nccreate | WM_NCCREATE | 視窗即将建立它的非客戶區 |
pbm_ncdestroy | WM_NCDESTROY | 視窗的非共享區被析構 |
pbm_nchittest | WM_NCHITTEST | 每次非客戶區被移動時都發送該消息 |
pbm_nclbuttondblclk | WM_NCLBUTTONDBLCLK | 使用者在非客戶區輕按兩下了滑鼠 |
pbm_ncpaint | WM_NCPAINT | 非客戶需要畫出 |
pbm_nextdlgctl | WM_NEXTDLGCTL | 在對話框中将焦點轉給另一個控件 |
pbm_paintclipboard | WM_PAINTCLIPBOARD | 剪貼闆應用有剪貼操作,剪貼闆檢視器需重畫 |
pbm_paint | WM_PAINT | 視窗的客戶區需要被畫出 |
PB 的事件 ID | 對應的系統消息 | 消息作用 |
pbm_palettechanged | WM_PALETTECHANGED | 系統調色闆被改變 |
pbm_paletteischanging | WM_PALETTEISCHANGING | 系統調色闆即将被改變 |
pbm_parentnotify | WM_PARENTNOTIFY | 通知父視窗一個子視窗即将被建立 |
pbm_querydragicon | WM_QUERYDRAGICON | 使用者要拖動一個最小化視窗 |
pbm_queryendsession | WM_QUERYENDSESSION | 通知消息,說明視窗即将被關閉 |
pbm_querynewpalette | WM_QUERYNEWPALETTE | 應用即将收到輸入焦點,應該執行必要的顔色調整 |
pbm_queryopen | WM_QUERYOPEN | 一個最小化視窗即将被恢複 |
pbm_quit | WM_QUIT | 應用處理的最後一個消息 |
續表
PB 的事件 ID | 對應的系統消息 | 消息作用 |
pbm_renderallformats | WM_RENDERALLFORMATS | 通知一個剪貼闆格式的擁有者,應用将失去所有的格式 |
pbm_renderformats | WM_RENDERFORMATS | 通知消息,說明放在剪貼闆中的資料應該用一種特殊格式傳送 |
pbm_setcursor | WM_SETCURSOR | 通知消息,說明滑鼠指針在一個視窗中 移動 |
pbm_setfont | WM_SETFONT | 用來設定對話框中的字型 |
pbm_setredraw | WM_SETREDRAW | 設定視窗是否重繪 |
pbm_settext | WM_SETTEXT | 用來設定視窗的标題欄文本 |
pbm_sizeclipboard | WM_SIZECLIPBOARD | 剪貼闆檢視器應用改變尺寸 |
pbm_spoolerstatus | WM_SPOOLERSTATUS | 一個列印管理器任務被添加或删除 |
pbm_syschar | WM_SYSCHAR | ALT 鍵和其他某鍵同時被按下 |
pbm_syscolorchange | WM_SYSCOLORCHANGE | 一種或多種系統顔色被改變 |
pbm_syscommand | WM_SYSCOMMAND | 視窗系統菜單控制消息 |
pbm_sysdeadchar | WM_SYSDEADCHAR | 通知消息,說明一種非英語字元集被標明 |
pbm_syskeydown | WM_SYSKEYDOWN | 使用者按下某鍵的同時按下了 ALT 鍵 |
pbm_syskeyup | WM_SYSKEYUP | 使用者釋放了 ALT 組合鍵 |
pbm_timechange | WM_TIMECHANGE | 系統時鐘被修改 |
pbm_undo | WM_UNDO | 從 undo 緩沖區複制文本到編輯器控件 |
pbm_vkeytoitem | WM_VKEYTOITEM | 當一個清單框擁有焦點時,使用者按下了一個鍵 |
pbm_vscroll | WM_VSCROLL | 使用者單擊了垂直滾動條 |
pbm_vscrollclipboard | WM_VSCROLLCLIPBOARD | 剪貼闆檢視器的垂直滾動條被單擊 |
pbm_windowposchanged | WM_WINDOWPOSCHANGED | 視窗位置發生改變 |
pbm_windowposchanging | WM_WINDOWPOSCHANGING | 視窗位置即将發生改變 |
pbm_wininichange | WM_WININICHANGE | WIN.INI 檔案被修改 |
( 6 )資料視窗( datawindow )控件自選事件:資料視窗控件是 PB 特有的一種控件對象。該控件的自選事件對視窗或其他控件許多消息進行了封裝,包括清單框消息、視窗滑鼠消息、滾動條消息,等等。由于 Sybase 公司并未公布資料視窗的内部機制,是以與系統消息的對應關系不得而知,但從事件 ID 的名稱可以略知一二,如 pbm_dwnlbuttondown 事件與滑鼠的 WM_LBUTTONDOWN 消息相對應 。資料視窗具體自選事件及其作用如表 1-7 所示。
表 1-7 資料視窗事件
PB 的事件 ID | 消息作用 |
pbm_dwclosedropdown | 關閉下拉式資料視窗 |
pbm_dwscrollend | 在資料視窗中卷滾到最後一行 |
pbm_dwscrollhome | 在資料視窗中卷滾到第一行 |
續表
PB 的事件 ID | 消息作用 |
pbm_dwscrolllineend | 卷滾到目前行的行尾(水準方向) |
pbm_dwscrolllinehome | 卷滾到目前行的行首(水準方向) |
pbm_dwnbacktabout | 即将通過 Shift+Tab 組合鍵離開該控件 |
pbm_dwnchanging | 控件即将被改變 |
pbm_dwndropdown | 下拉式清單框的下拉部分即将可見 |
pbm_dwngraphcreate | 即将建立圖形 |
pbm_dwnitemchangefocus | 資料視窗控件中目前項的焦點改變 |
pbm_dwnitemvalidationerror | 對目前項的修改引起了一個合法性檢查錯誤 |
pbm_dwnkey | 有鍵被按下。使用 KeyDown() 處理鍵盤值 |
pbm_dwnlbuttondown | 滑鼠左鍵被按下 |
pbm_dwnlbuttonup | 滑鼠左鍵被松開 |
pbm_dwnmbuttonclk | 滑鼠中鍵單擊 |
pbm_dwnmbuttondbclk | 滑鼠中鍵輕按兩下 |
pbm_dwnmousemove | 滑鼠移動 |
pbm_dwnprintmarginchange | 列印邊界被改變 |
pbm_dwnprocessenter | Enter鍵被按下 |
pbm_dwnrowchange | 資料視窗中焦點從一行轉向另一行 |
pbm_dwntabdownout | 使用者在資料視窗最後一行按了下箭頭鍵 |
pbm_dwntabout | 使用者在資料視窗的最後一行 / 列中按了 Tab 鍵 |
pbm_dwntabupout | 使用者在資料視窗第一行中按了上箭頭鍵 |
( 7 )動态資料交換( DDE )事件及對應的系統消息,如表 1-8 所示。
表 1-8 動态資料交換 (DDE) 事件及對應的系統消息
PB 的事件 ID | 對應的系統消息 | 消息作用 |
pbm_ddeddeack | WM_DDE_ACK | 收到一個 DDE 消息 |
pbm_ddeddeinitiate | WM_DDE_INITIATE | 開始一個 DDE 會話 |
pbm_ddeddeterminate | WM_DDE_TERMINATE | 終止一個 DDE 會話 |