• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            Chip Studio

            常用鏈接

            統計

            最新評論

            property

            delphi的屬性property和消息處理特點事件屬性。

            Delphi  中的屬性property(適合初學delphi)
            Propery In Delphi

            前言:
            適合delphi初學者,有面向對象知識和java或者vc編程經驗人士閱讀。
            一普通屬性
            我們在delphi的類中常常能看到這樣的代碼:propert property 屬性名 類型名 read 字符串1 write 字符串2
            這里屬性的名字可能不同。都是這樣的格式:property 屬性名 read 字符串1 write 字符串2
            我以property Left: Integer read FLeft write SetLeft;為例子,它是Tcontrol的屬性,你可以在controls文件中找到。Left是一個Integer類型的屬性。Read申明了訪 問該變量要訪問的變量或者方法,write申明了修改該變量時訪問的變量或者方法。注意:可以是變量,也可以是方法,我在后面告訴大家這是怎么回事。這里 它是一個變量,名字叫做FLeft。出于封裝的目的,我們一般都會把這樣的變量放在private中間去,果然,在private中我們可以找到
            FLeft: Integer這段代碼(出于命名的習慣,我們把這樣的變量取名為屬性名前面加一個大寫的F)。這樣當你read該屬性時,實際上你訪問的是Fleft的 值。所以你可以寫些方法來修改fleft,間接修改了left的值。然后我們再看SetLeft,這里它是一個方法(問我怎么知道?還是看命名規則,通常 用屬性名前面加上Set),通常也會放在private中去,我們來驗證一下,我們在private中看到申明:
            procedure SetLeft(Value: Integer);
            和如下代碼實現:
            procedure TControl.SetLeft(Value: Integer);
            begin
              SetBounds(Value, FTop, FWidth, FHeight);
              Include(FScalingFlags, sfLeft);
            end;
            如果你寫了如下代碼改變left:control1.left:=23,那么程序調用了函數SetLeft(23),SetBounds是改變區域的函 數,這里你就明白了它封裝了的好處,每次你改變left時它就會根據新的left而改變區域的大小,這個函數同時也改變了Fleft的大小,請查閱 SetBounds的源代碼。
            procedure TControl.SetBounds(ALeft, ATop, AWidth, AHeight: Integer);
            begin
              if CheckNewSize(AWidth, AHeight) and
                ((ALeft <> FLeft) or (ATop <> FTop) or
                (AWidth <> FWidth) or (AHeight <> FHeight)) then
              begin
                InvalidateControl(Visible, False);
                FLeft := ALeft;
                FTop := ATop;
                FWidth := AWidth;
                FHeight := AHeight;
                UpdateAnchorRules;
                Invalidate;
                Perform(WM_WINDOWPOSCHANGED, 0, 0);
                RequestAlign;
                if not (csLoading in ComponentState) then Resize;
              end;
            end;
            這樣外部就看起來只是通過賦值運算來改變了該屬性的值。Read和write可以是變量,或者是函數,取決于你的設計。你當然可以這樣寫: propert property 屬性名 類型名 read 變量1 write 變量2。變量1和變量2可以是相同的。你也可以這樣propert property 屬性名 類型名 read 方法1 write 方法2。任你組合。但是有2點要注意:
            1.         命名規則最好按習慣來,易于閱讀。
            2.         如果是變量,那么類型要和屬性的類型一致,如果是方法,那么入口參數要和屬性的類型一致。
            二事件屬性Tevent
            我們常常使用組件的事件屬性,比方說click事件,可是我們很難從表面看出它是如何調用的呢,如何觸發的呢。下面我來給你解答。
            我們在屬性管理器object inspector中看到event頁onclick右邊對應了一個方法的名字。我們其實可以這樣給一個組件的事件對應上一個出來方法。以一個form為 例子Form1. OnMouseDown:=‘你的方法‘。注意方法的入口參數有講究,這里是(Sender:TObject)
            我們還是一tcontrol為例子,我們找到這段代碼:
            property OnMouseDown: TMouseEvent read FOnMouseDown write FOnMouseDown;跟上面講的類似,不過這里有個特殊的類型,TNOtifyEvent,是個事件類型,我們找到它的申明:
            TMouseEvent = procedure(Sender: TObject; Button: TMouseButton;Shift: TShiftState; X, Y: Integer) of object;
            可以看到,它其實就是個函數,但是藍色部分把入口參數限定了。那么我們通過賦值Form1. OnMouseDown:=‘你的方法‘,就對應了OnMouseDown的方法。然后我們只要寫了一段攔截鼠標消息的函數,在里面直接或間接調用 FonMouseDown,那么就把消息和處理函數對應上去了。這里它間接調用的層數比較多,講起來比較費時間,涉及到Message類型,建議大家去看 下李維的書。
            以下附上間接調用過程,其實還要很多消息發生時也間接調用了,就不一一舉出來了:(

            procedure WMRButtonDblClk(var Message: TWMRButtonDblClk); message WM_RBUTTONDBLCLK;//攔截消息的函數
            procedure TControl.WMRButtonDblClk(var Message: TWMRButtonDblClk);
            begin
              inherited;
              DoMouseDown(Message, mbRight, [ssDouble]);
            end;

            procedure DoMouseDown(var Message: TWMMouse; Button: TMouseButton;
            Shift: TShiftState);
            procedure TControl.DoMouseDown(var Message: TWMMouse; Button: TMouseButton;
              Shift: TShiftState);
            begin
              if not (csNoStdEvents in ControlStyle) then
                with Message do
                  if (Width > 32768) or (Height > 32768) then
                    with CalcCursorPos do
                      MouseDown(Button, KeysToShiftState(Keys) + Shift, X, Y)
                  else
                    MouseDown(Button, KeysToShiftState(Keys) + Shift, Message.XPos, Message.YPos);
            end;

            procedure MouseDown(Button: TMouseButton; Shift: TShiftState;
            X, Y: Integer); dynamic;
            procedure TControl.MouseDown(Button: TMouseButton;
              Shift: TShiftState; X, Y: Integer);
            begin
              if Assigned(FOnMouseDown) then FOnMouseDown(Self, Button, Shift, X, Y);
            end;

            好處:
            如果你多寫自己的類,你會發現這樣做是多么的方便,而不會像java要寫getleft,setleft,然后把text放在private中,訪問和修 改時要調用不同的方法,而delphi你都只是調用contol1.text來訪問,control1.text:=’某字符串’來修改它的值。
            而在處理消息方面,基類把onclick,onmousedown這樣的屬性申明為protected,如果你要使用,可以申明為published就可 以出現在object inspector里面,然后方便的寫處理方法,你也可以不公開,而在ctreate函數中給它賦值,而不用像java那樣,寫listener那么復 雜。
            我的研究也不深,有什么不妥請指正:)。歡迎來信wenjunwu430@163.com

            posted on 2008-02-14 17:08 MyChip 閱讀(94) 評論(0)  編輯 收藏 引用

            欧美一区二区久久精品| 久久精品无码一区二区app| 久久er99热精品一区二区| 久久国产高清字幕中文| 精品国产日韩久久亚洲| 国产综合久久久久久鬼色| 久久夜色精品国产亚洲| 少妇久久久久久被弄高潮| 综合久久精品色| 天堂无码久久综合东京热| 久久精品国产一区二区三区日韩| 精品久久久久成人码免费动漫 | 国产亚洲美女精品久久久久狼| 欧美一级久久久久久久大片| 国产精品成人99久久久久| 一本色道久久88加勒比—综合| 91精品国产91久久久久久蜜臀| 久久久精品人妻一区二区三区四| 久久久久se色偷偷亚洲精品av | 欧美精品丝袜久久久中文字幕 | 久久国产综合精品五月天| 久久婷婷五月综合97色直播| 伊人久久国产免费观看视频| 欧美喷潮久久久XXXXx| 99久久精品国产一区二区| 午夜肉伦伦影院久久精品免费看国产一区二区三区 | 久久99精品久久久久久| 狠狠色丁香久久婷婷综合_中| 国产精品天天影视久久综合网| 久久93精品国产91久久综合| 久久国产亚洲高清观看| 要久久爱在线免费观看| 伊人丁香狠狠色综合久久| 国产偷久久久精品专区| 精品多毛少妇人妻AV免费久久| 香蕉久久夜色精品升级完成| 99久久精品免费| 久久久久99精品成人片牛牛影视| 久久久久久人妻无码| 7777久久亚洲中文字幕| 囯产极品美女高潮无套久久久|