寫元件時作 Free 前儲存元件屬性的時機 |
尚未結案
|
Justmade
版主 發表:94 回覆:1934 積分:2030 註冊:2003-03-12 發送簡訊給我 |
|
ha0009
版主 發表:16 回覆:507 積分:639 註冊:2002-03-16 發送簡訊給我 |
你好:
如果我沒記錯的話,繼承自 TPersistent 的物件可改寫 DefineProperties 程序來達成你的目的。以下摘錄自 Help 的 Demo。 // 這是元件載入屬性的程序。
procedure TSampleComponent.LoadCompProperty(Reader: TReader);
begin
if Reader.ReadBoolean then
MyCompProperty := Reader.ReadComponent(nil);
end; // 這是元件儲存屬性的程序。
procedure TSampleComponent.StoreCompProperty(Writer: TWriter);
begin
Writer.WriteBoolean(MyCompProperty <> nil);
if MyCompProperty <> nil then
Writer.WriteComponent(MyCompProperty);
end; // 在這個程序設定某屬性的載入與儲存的方法。
procedure TSampleComponent.DefineProperties(Filer: TFiler);
function DoWrite: Boolean;
begin
if Filer.Ancestor <> nil then { check Ancestor for an inherited value }
begin
if TSampleComponent(Filer.Ancestor).MyCompProperty = nil then
Result := MyCompProperty <> nil
else if MyCompProperty = nil or
TSampleComponent(Filer.Ancestor).MyCompProperty.Name <> MyCompProperty.Name then
Result := True else Result := False;
end
else { no inherited value -- check for default (nil) value }
Result := MyCompProperty <> nil;
end;
begin
inherited; { allow base classes to define properties }
Filer.DefineProperty('MyCompProperty', LoadCompProperty, StoreCompProperty, DoWrite);
end;
}
|
Justmade
版主 發表:94 回覆:1934 積分:2030 註冊:2003-03-12 發送簡訊給我 |
ha009 兄 謝謝你的回應。 不過,我不是要知道如何存取屬性,事實上我的元件已可以自由存取 Form 中所有元件 published 的屬性。 可以隨時儲存到檔案及讀回Load到 Form / Container / Component 中。 只是我想加入 AutoSave 功能, AutoLoad 在 元件的 Loaded 執行沒問題 但 AutoSave 在 BeforeDestruction 執行當使用 IsDefaultPropertyValue(...) 時會 AV 謝謝。
|
Justmade
版主 發表:94 回覆:1934 積分:2030 註冊:2003-03-12 發送簡訊給我 |
|
syntax
尊榮會員 發表:26 回覆:1139 積分:1258 註冊:2002-04-23 發送簡訊給我 |
如果我沒會錯意的話
他的回答正是你所需要的
只是你還需要自己寫 component editor 來控制 Load/Save 與 在 desogn time 時重置 form 來符合新 load 進來的東東 !
引言: ha009 兄 謝謝你的回應。 不過,我不是要知道如何存取屬性,事實上我的元件已可以自由存取 Form 中所有元件 published 的屬性。 可以隨時儲存到檔案及讀回Load到 Form / Container / Component 中。 只是我想加入 AutoSave 功能, AutoLoad 在 元件的 Loaded 執行沒問題 但 AutoSave 在 BeforeDestruction 執行當使用 IsDefaultPropertyValue(...) 時會 AV 謝謝。 |
Justmade
版主 發表:94 回覆:1934 積分:2030 註冊:2003-03-12 發送簡訊給我 |
引言: 如果我沒會錯意的話 他的回答正是你所需要的 只是你還需要自己寫 component editor 來控制 Load/Save 與 在 desogn time 時重置 form 來符合新 load 進來的東東 !謝謝你的回覆,可能我說得不夠清楚罷(由其是在第一篇 post 時),所以 ha0009 兄確是提了一個一般來說非常合適的方案 但問題是 : 1. 我不是用 WrtieComponent 機制來 Save/Load 2. 我的對像不是 元件本身而是整個 Form / 其他某些 Container 及其他元件 / 某特定元件 所以應根本不會觸動 LoadCompProperty / SaveCompProperty 應跟本沒呼叫 ReadComponent / WriteComponent。 |
syntax
尊榮會員 發表:26 回覆:1139 積分:1258 註冊:2002-04-23 發送簡訊給我 |
引言:所以我才說,你得自己寫這一部份的程式碼啊,讓你可以除了在 Delphi Load/Save From 時之外,也能手動 Load/Save,同時在讀取後也要加程式碼來更新那些不在正規下會自動更新的部分,所以本來只是需要用到 Property Editor,現在還要加上 Component Editor 兩者同時修改來符合你的需要! 不過要在 Runtime 做,這根本就是自己寫一個 Delphi 介面嬤!那這樣 Dlphi 的方法直接拿來用不是比較省事嗎? 參考 ToolAPI 的內部程式碼也許有幫助! 如過你不願用 Property Editor 的 Read/WrtieComponent 來 Load/Save 那你就必須要先了解你的目的與元件的生死,這樣才能在最佳的位置差放你的程式碼! 一般在進入BeforeDestruction後就代表元件已經進入摧毀階段!這時是很敏感的!不能去呼叫已經被摧毀的東西喔!同時要判斷哪些已經摧毀了!這樣很麻煩!用在 OnClose 的好處是,OnClose 在 BeforeDestruction 之前被呼叫,此時還不算是摧毀階段,內部的元件也都尚未通知進入摧毀程序,這樣就不會呼叫到已被摧毀的內涵元件而出錯!另外 Inherited 這個呼叫在 BeforeDestruction 內與你的程式碼的先後次序也有嚴重的相依性,次序不同可能會有錯誤或是沒錯誤之不同! 所以 IsDefaultPropertyValue(...) 便會 Access Violation 應該是該元件已摧毀,而你還去呼叫他所產生的錯誤!(應該是這樣吧!) 所以元件的生死流程你要很清楚!這樣才不會有出錯的狀況! 從這方面著手仔細追蹤你的程式,應該是能找到問題點! 不過挺累人的! 祝你好運! 發表人 - syntax 於 2003/06/10 23:25:58引言: 如果我沒會錯意的話 他的回答正是你所需要的 只是你還需要自己寫 component editor 來控制 Load/Save 與 在 desogn time 時重置 form 來符合新 load 進來的東東 !謝謝你的回覆,可能我說得不夠清楚罷(由其是在第一篇 post 時),所以 ha0009 兄確是提了一個一般來說非常合適的方案 但問題是 : 1. 我不是用 WrtieComponent 機制來 Save/Load 2. 我的對像不是 元件本身而是整個 Form / 其他某些 Container 及其他元件 / 某特定元件 所以應根本不會觸動 LoadCompProperty / SaveCompProperty 應跟本沒呼叫 ReadComponent / WriteComponent。 |
Justmade
版主 發表:94 回覆:1934 積分:2030 註冊:2003-03-12 發送簡訊給我 |
引言: 所以我才說,你得自己寫這一部份的程式碼啊,讓你可以除了在 Delphi Load/Save From 時之外,也能手動 Load/Save,同時在讀取後也要加程式碼來更新那些不在正規下會自動更新的部分,所以本來只是需要用到 Property Editor,現在還要加上 Component Editor 兩者同時修改來符合你的需要! 不過要在 Runtime 做,這根本就是自己寫一個 Delphi 介面嬤!那這樣 Dlphi 的方法直接拿來用不是比較省事嗎? 參考 ToolAPI 的內部程式碼也許有幫助! 如過你不願用 Property Editor 的 Read/WrtieComponent 來 Load/Save 那你就必須要先了解你的目的與元件的生死,這樣才能在最佳的位置差放你的程式碼! 一般在進入BeforeDestruction後就代表元件已經進入摧毀階段!這時是很敏感的!不能去呼叫已經被摧毀的東西喔!同時要判斷哪些已經摧毀了!這樣很麻煩!用在 OnClose 的好處是,OnClose 在 BeforeDestruction 之前被呼叫,此時還不算是摧毀階段,內部的元件也都尚未通知進入摧毀程序,這樣就不會呼叫到已被摧毀的內涵元件而出錯!另外 Inherited 這個呼叫在 BeforeDestruction 內與你的程式碼的先後次序也有嚴重的相依性,次序不同可能會有錯誤或是沒錯誤之不同! 所以 IsDefaultPropertyValue(...) 便會 Access Violation 應該是該元件已摧毀,而你還去呼叫他所產生的錯誤!(應該是這樣吧!) 所以元件的生死流程你要很清楚!這樣才不會有出錯的狀況! 從這方面著手仔細追蹤你的程式,應該是能找到問題點! 不過挺累人的! 祝你好運!1. 請看看 Help, BeforeDestruction 時所有原件都未 Destroy 的,只是在 ComponentState 改上 csDestroying 2. 使用 read/write Component 有很多問題丫自由度又低 3. 照你的說法若要給使用者較高自由度的自定介面就要每個使用者都要裝一個 Delphi 拿你的 Sources Code 來重新 Complie 了? 4. 若我不知放在 FormClose 的好處便不回放暫以此為解決之道了,但也有問題如執行 FormClose 後不一定真的 Close (可能 Close Action 是 Hide / Minimize 甚至是 None),所以才發問丫,結果還得到的只是一堆『!』。 |
syntax
尊榮會員 發表:26 回覆:1139 積分:1258 註冊:2002-04-23 發送簡訊給我 |
引言: 1. 請看看 Help, BeforeDestruction 時所有原件都未 Destroy 的,只是在 ComponentState 改上 csDestroying 2. 使用 read/write Component 有很多問題丫自由度又低 3. 照你的說法若要給使用者較高自由度的自定介面就要每個使用者都要裝一個 Delphi 拿你的 Sources Code 來重新 Complie 了? 4. 若我不知放在 FormClose 的好處便不回放暫以此為解決之道了,但也有問題如執行 FormClose 後不一定真的 Close (可能 Close Action 是 Hide / Minimize 甚至是 None),所以才發問丫,結果還得到的只是一堆『!』。1.你也用不著不高興,會得到一堆『!』,也是因為沒人看到你的程式碼,用猜的,當然只能得到一堆『!』,同時在 ComponentState 改上 csDestroying 就對程式的運作有影響力了,當然 BeforeDestruction 時所有原件都未 Destroy ,但是還是會產生錯誤,你以為 Access Violation 是哪種錯誤的結果啊,再說即使 FormClose 後被 Abort 或是....等等,不是真的 Close ,只不過是 save ,多存一次有關係嗎,除非存一次要幾十分鐘,要不然沒差別啊。 2.看程式寫作功力,不然那開發 Delphi 的設計者,豈不是撞牆去,有人會開發自己認為不好用、不自由的東西來說服自己他很好用、很自由的來賣嗎?應該是不會吧。 3.我可沒這麼說,只是你的東西跟 Delphi 有什麼不同,還不都一樣,讓使用者有較高的自由度來自訂使用介面是不錯的想法,但是你的方式比較死板而已,可以運用的不是只有這種方法啊,何必一定要做的跟 Delphi 一樣,這樣會讓人弄模糊你那麼好的設計用意阿。 4.既然你那麼不喜歡『!』,那我不用就是囉。 |
Justmade
版主 發表:94 回覆:1934 積分:2030 註冊:2003-03-12 發送簡訊給我 |
1.
沒人看見程式碼就"當然只能得到一堆『!』",是甚麼思考邏輯?
前一文說在 BeforeDestruction "不能去呼叫已經被摧毀的東西喔!同時要判斷哪些已經摧毀了!這樣很麻煩!",給指出錯誤後現在又大聲說 "當然 BeforeDestruction 時所有原件都未 Destroy",好像一直對的是你,是甚麼的做人態度?
在這個 Case 多存一次是沒多大關係但會多存就是代表時機不正確,可以的話不是應找更正確的事機有錯嗎?明知不好但就因循的了事,還要別人也學你這樣做,是甚麼的工作態度? 我說過我的第一篇 post 沒說清楚我不是用 read/write component 所以 ha0009 的答案是很合理的。不過之後我已說清楚了這點了。除了這點之外,跟本就與程式碼無關。我已說清楚了在 BeforeDestruction 中使用 IsDefaultPropertyValue 會出錯,在 FormClose 可以但時機應不是最好。對於不懂 IsDefaultPropertyValue 的人,貼出一大堆程式碼也不會有用。 2.
read/write component 的設計主要是 Delphi designtime存檔及designtime/runtime 起始時讀檔建立元件之用,對滿足他們自己這個要求來說是合用的,對不少其他操作這個設計也很好用,但這不等於在所有相關情況下都合用。不能符合所有需要不是甚麼大不了的事,開發者也不用撞牆去,否則所有軟件只出一個版本就好了,不用出第二個版本否則便應撞牆去了。
自己認為很好用很自由不一定在別人眼中很好用很自由,Delphi 的架構就是知道自己雖然已很好用但仍不會滿足所有需要,所以讓使用者可以自行承繼元件,加入 Expert/Property Editor 等等,若像你所說的,這些都不需要了否則開發元件/介面者便要去撞牆了。 3.
你不是說"不過要在 Runtime 做,這根本就是自己寫一個 Delphi 介面嬤!那這樣 Dlphi 的方法直接拿來用不是比較省事嗎?",現在又說沒這樣說,轉得真快。不要以為每個程式設計師寫的程式都是只給自己用的或一兩個人用的,要改可以拿到 Delphi 改就好。也不要以為自己設計的就是最合每一個使用者用的。 大部份商業軟體的視窗都跟 Windows 本身很像,是不是有版權間題?從 Windows 3.X 時代的 Object Orianted 開發軟件,差不多每一個也是有類似的 Property Editor 的,有甚麼與 Delphi 像不像?該不會是你只看過 Delphi 沒見過其他開發軟件罷?再者,Property Edito 會從頭到現在都在用的原因,就是因為他是已知的最方便設定 property 的方式(可能有些未知的更好的方法等你來發表)。另外,我的 Property Editor 將會是可自行設計的,只要支援指定的 interface 便可以。 "讓使用者有較高的自由度來自訂使用介面是不錯的想法,但是你的方式比較死板而已,可以運用的不是只有這種方法啊,何必一定要做的跟 Delphi 一樣,這樣會讓人弄模糊你那麼好的設計用意阿。" 空口說白話誰人不會,發表一個出來給去做褔廣大的網友罷。 4.
我不是不喜歡『!』只是認為應在合適的時間才用。就正如人有是確是需要大叫但不應像有些小童一直在亂叫。 最後我發表問題是希望對問題本身作論論,對於其他部份除非能拿出一些實質的更好做法或提議,否則我是沒時間對那些天馬行空的指指點點作回應的了,先此致歉。
|
本站聲明 |
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。 2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。 3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇! |