---- 1. เคล็ดลับในการใช้การควบคุมแบบต้นไม้ใน Delphi
---- เราทุกคนรู้ดีว่านักพัฒนาส่วนใหญ่ใช้ Delphi เพื่อพัฒนาซอฟต์แวร์การจัดการฐานข้อมูล ด้วยเหตุนี้ การใช้การควบคุมแบบต้นไม้จึงเชื่อมโยงกับฐานข้อมูลได้ดีที่สุด Delphi มีการควบคุมแบบต้นไม้ TTreeView ซึ่งสามารถใช้เพื่ออธิบายความสัมพันธ์แบบลำดับชั้นที่ซับซ้อน
---- 1. การจัดเก็บและการโหลดข้อมูลโหนดต้นไม้
---- วิธีการที่ใช้กันทั่วไปคือการใช้วิธีการ LoadFromFile และ SavetoFile ของตัวควบคุมแผนผังเพื่อให้ทราบถึงการโต้ตอบระหว่างตัวควบคุมแผนภูมิและไฟล์ หรือใช้วิธีการกำหนดเพื่อให้ทราบถึงการโต้ตอบระหว่างตัวควบคุมแผนภูมิและ DBMemo นั่นคือ การโต้ตอบกับฐานข้อมูล ข้อดีของวิธีนี้คือการเขียนโปรแกรมค่อนข้างง่าย ข้อเสียคือจำนวนโหนดจริงในการควบคุมแผนผังอาจมีขนาดใหญ่มาก สำหรับ "ต้นไม้ใหญ่" ปริมาณข้อมูลที่โหลดและจัดเก็บในแต่ละครั้งจะเพิ่มขึ้น ซึ่งจะ ลดความเร็วและเพิ่มโอเวอร์เฮดของระบบ ส่งผลให้ Data redundancy อีกวิธีหนึ่งคือสร้างเฉพาะโหนด "ที่มองเห็นได้" ในแผนผัง โดยไม่มีไฟล์หรือฟิลด์ฐานข้อมูลที่บันทึกโครงสร้างโหนดแผนผังทั้งหมดโดยเฉพาะ และเพื่อกระจายโครงสร้างโหนดแผนผังในแต่ละบันทึกของฐานข้อมูล
---- วิธีการเฉพาะคือ: สร้างฐานข้อมูล ฟิลด์จะถูกกำหนดตามธุรกิจจริง จะต้องมีหนึ่งฟิลด์ที่ข้อมูลจะถูกแสดงบนโหนดของการควบคุมแบบต้นไม้ และยังมีฟิลด์สำหรับบันทึก หมายเลขประจำตัวที่ไม่ซ้ำกันของโหนด หมายเลขประจำตัวประกอบด้วยสองส่วนที่มีความยาวเท่ากัน ส่วนแรกแสดงถึงหมายเลขโหนดหลักของโหนดปัจจุบัน และส่วนหลังแสดงถึงหมายเลขโหนดของหมายเลขประจำตัวปัจจุบัน "รายการที่เชื่อมโยง" ที่บันทึกโครงสร้างของโหนดบนแผนผัง ข้อดีของวิธีนี้: เมื่อผู้ใช้ใช้งาน "ต้นไม้ใหญ่" โดยทั่วไปแล้วพวกเขาจะไม่ขยายโหนดทั้งหมด แต่จะใช้เฉพาะส่วนที่จำกัดเท่านั้น ในเวลาเดียวกัน พวกเขาสามารถขยายได้ทีละชั้นจากรากของต้นไม้เท่านั้น วิธีการสร้าง "" บนแผนผังเท่านั้น ดังนั้น ความเร็วในการจัดเก็บและการโหลด "ต้นไม้ใหญ่" จึงรวดเร็ว ปริมาณข้อมูลมีน้อย และโอเวอร์เฮดของระบบและความซ้ำซ้อนของข้อมูลมีน้อย ข้อเสีย: การเขียนโปรแกรมมีความซับซ้อนมากกว่า แต่วิธีการนี้สามารถนำมารวมกันเพื่อสร้างการควบคุมแผนผังใหม่ ซึ่งจะช่วยปรับปรุงประสิทธิภาพการเขียนโปรแกรมอย่างมาก เป็นที่น่าสังเกตว่าหมายเลข ID จะต้องไม่ซ้ำกัน ดังนั้นวิธีสร้าง ID อย่างสมเหตุสมผลในการเขียนโปรแกรมจึงมีความสำคัญอย่างยิ่ง
---- 2. ตัวอย่างโครงสร้างฐานข้อมูล
----สร้างฐานข้อมูลเพื่อให้ขั้นตอนง่ายขึ้น ฉันสร้างเพียงสองฟิลด์ฐานข้อมูล กำหนดดังนี้:
ความยาวประเภทชื่อฟิลด์
ข้อความC10
ลองไอดีซี6
---- จริงๆ แล้วฟิลด์ LongID ประกอบด้วยสองส่วน โดยแต่ละส่วนจะมีตัวเลข 3 หลัก กำหนด LongID เป็นฟิลด์ดัชนีและบันทึกเป็น c: esttree ree.dbf แก้ไขไฟล์ DBF สร้างบันทึกใหม่ ตั้งค่าฟิลด์ข้อความเป็น TOP และตั้งค่าฟิลด์ LongID เป็น "000" (ช่องว่างสามช่องก่อนสาม "0")
---- 3. สร้างโปรแกรมสาธิต
---- วาง TreeView1, Table1, PopupMenu1, Edit1 และ Edit2 บน Form1 คุณลักษณะ PopupMenu ของ TreeView1 ถูกตั้งค่าเป็น PopupMenu1; DataBaseName แอตทริบิวต์ของ Table1 ถูกตั้งค่าเป็น c: esttree, คุณลักษณะ TableName ถูกตั้งค่าเป็น tree.dbf และแอตทริบิวต์ IndexFieldNames ถูกตั้งค่าเป็น LongID; และคำบรรยายคือ Add และ Del ตามลำดับ Edit1 ใช้ในการป้อนค่าแอตทริบิวต์ Text ของโหนดใหม่ Edit2 ใช้เพื่อป้อนหมายเลข ID 3 หลักของโหนดใหม่ บันทึกเป็น c:esttree reeunit.pas และ c:esttree esttree.dPR เพิ่มบรรทัดหลังคีย์เวิร์ด Type ใน treeunit.pas: Pstr:^string;{Pstr is a string pointer} เพิ่มโค้ดสำหรับเหตุการณ์ OnCreate ของ Form1:
ขั้นตอน TForm1.FormCreate (ผู้ส่ง: TObject);
var p:Pstr;โหนด:TTreeNode;
เริ่ม
ด้วย Table1, Treeview1 ทำ
เริ่ม
เปิด;
อันดับแรก;
ใหม่ (p); {จัดสรรหน่วยความจำสำหรับตัวชี้ p}
p^:=FieldByName(′LongID′).AsString;
โหนด:=Items.AddChildObject(ไม่มี,FieldByName
('ข้อความ').AsString,p);
ถ้า HasSubInDbf(Node) แล้วรายการ
.AddChildObject(Node,′ ′,nil);{หากมีโหนดลูก ให้เพิ่มโหนดลูกว่าง}
จบ;
จบ;
---- HasSubInDbf เป็นฟังก์ชันที่กำหนดเอง ตัวแปรอิสระคือ Node ตรวจสอบว่าโหนดโหนดมีโหนดย่อยหรือไม่ คืนค่า True หากมี มิฉะนั้นจะคืนค่าเท็จ และเพิ่มการประกาศต้นแบบให้กับคำจำกัดความคลาสของ TForm1 (ต้นแบบของ ฟังก์ชันแบบกำหนดเองอื่นๆ จะถูกประกาศในคำจำกัดความคลาสของ TForm1 โดยไม่มีคำอธิบายเพิ่มเติม) โค้ดฟังก์ชันจะเป็นดังนี้:
ฟังก์ชัน TForm1.HasSubInDbf(โหนด:TTreeNode):บูลีน;
เริ่ม
ด้วย Table1 ทำ
เริ่ม
Table1.FindNearest([คัดลอก(Pstr(Node.Data)^,4,3)+′000′]);
ผลลัพธ์:=copy(FieldByName('LongID')
AsString,1,3)=copy(Pstr(Node.Data)^,4,3);
{ตัวอย่างเช่น ผลรวมของตัวเลขสามหลักแรกของเนื้อหาฟิลด์ LongID ของบันทึกปัจจุบันในฐานข้อมูล
หากตัวเลขสามหลักสุดท้ายของข้อมูลของโหนดโหนดเหมือนกัน ดังนั้นโหนดควรมีโหนดลูก}
จบ;
จบ;
เพิ่มโค้ดสำหรับเหตุการณ์ OnDeletion ของตัวควบคุม TreeView1 ควรชี้ให้เห็นว่า
ไม่เพียงแต่สามารถทริกเกอร์เหตุการณ์ OnDeletion ได้โดยการเรียกเมธอด Delete แต่ยังก่อนที่ตัวควบคุมแผนผังจะถูกปล่อยออกมาด้วย
เหตุการณ์ OnDeletion ยังถูกทริกเกอร์ ดังนั้นจึง "ปลอดภัย" ที่จะเพิ่ม dispose(node.data) ที่นี่:
ขั้นตอน TForm1.TreeView1Deletion
(ผู้ส่ง: TObject; โหนด: TTreeNode);
เริ่ม
กำจัด (Node.Data); {ปล่อยหน่วยความจำข้อมูลโหนด}
จบ;
เพิ่มรหัสต่อไปนี้ลงในเหตุการณ์ OnClick ของรายการเมนู Add1:
ขั้นตอน TForm1.Add1Click (ผู้ส่ง: TObject);
var p:pstr;Tmpstr:สตริง;i:จำนวนเต็ม;
เริ่ม
พยายาม
StrToInt(แก้ไข2.ข้อความ);
Tmpstr:=Edit2.Text;{หมายเหตุ: ในทางปฏิบัติ ต้องใช้วิธีที่ดีกว่าในการสร้าง ID}
ยกเว้น;
ShowMessage('ป้อนเนื้อหาของ Edit2 อีกครั้ง');
ยกเลิก;
จบ;
ด้วย TreeView1 ทำ
เริ่ม
ใหม่(พี);
p^:=copy(Pstr(Selected.Data)^,4,3)+TmpStr;
Items.AddChildObject(เลือกแล้ว,แก้ไข1.ข้อความ,p);
จบ;
ด้วย Table1 ทำ {เพิ่มบันทึกในฐานข้อมูล}
เริ่ม
ผนวก;
FieldByName('Text').AsString:=Edit1.text;
FieldByName('LongID').AsString:=p^;
โพสต์;
จบ;
TmpStr:=inttostr(strtoint(TmpStr)+1);
สำหรับ i:=length(TmpStr) ถึง 2 ทำ TmpStr:=′0′+TmpStr;
แก้ไข2.ข้อความ:=TmpStr;
จบ;
เพิ่มรหัสต่อไปนี้ลงในเหตุการณ์ OnClick ของรายการเมนู Del1:
ขั้นตอน TForm1.Del1Click (ผู้ส่ง: TObject);
var DelList:TStringList;LongID,NSubLongID:สตริง;
เริ่ม
DelList:=TStringList.create;
DelList.Sorted:=จริง;
DelList.Add(Pstr(TreeView1.Selected.Data)^);
ในขณะที่ DelList.Count>0 ทำ
เริ่ม
LongID:=DelList.Strings[0];
DelList.Delete(0);
Table1.SetKey;
Table1.FieldByName(′LongID′).AsString:=LongID;
ถ้า Table1.GotoKey แล้วก็ Table1.Delete;
ถ้า HasSubInDbf(TreeView1.Selected) แล้ว
เริ่ม
NSubLongID:=Table1.FieldByName('LongID').AsString;
ในขณะที่ (คัดลอก (NSubLongID,1,3)=copy
(LongID,4,3))และ(ไม่ใช่ Table1.Eof) ทำ
เริ่ม
dellist.Add(NSubLongId);
Table1.ถัดไป;
NSubLongId:=Table1.FieldByName('LongID').AsString;
จบ;
จบ;
จบ;
DelList ฟรี;
TreeView1.Items.Delete (TreeView1.Selected);
จบ;
เพิ่มโค้ดสำหรับเหตุการณ์ OnExpanding ของ TreeView1:
ขั้นตอน TForm1.TreeView1Expanding
(ผู้ส่ง: TObject; โหนด: TTreeNode;
var AllowExpansion: บูลีน);
var TmpNode:TTreeNode;NSubLongID:
สตริง;p:Pstr;bm:TBookMark;
เริ่ม
ด้วย Table1, TreeView1 ทำ
เริ่ม
รายการ BeginUpdate;
เซ็ตคีย์;
FieldByName('LongID').AsString:=Pstr(Node.Data)^;
ถ้าไม่ใช่ GotoKey ดังนั้น Items.Delete(Node)
อื่น
เริ่ม
TmpNode:=Node.GetFirstChild;
ถ้า (TmpNode.Text=′ ′)และ(TmpNode.Data=nil) แล้ว
เริ่ม
TmpNode ลบ;
ถ้า HasSubInDbf(Node) แล้ว
เริ่ม
NSubLongID:=FieldByName('LongID').AsString;
ในขณะที่ (คัดลอก (NSubLongID,1,3)=คัดลอก(Pstr
(Node.Data)^,4,3))และ(ไม่ใช่ Eof) ทำ
เริ่ม
ใหม่(พี);
p^:=FieldByName(′LongID′).AsString;
bm:=GetBookMark;
TmpNode:=Items.AddChildObject(โหนด
FieldByName('ข้อความ').AsString,p);
ถ้า HasSubInDbf(TmpNode) แล้วรายการ
AddChildObject(TmpNode,′′,ไม่มี);
ไปที่BookMark(bm);
ฟรีบุ๊คมาร์ก(bm);
ต่อไป;
NSubLongId:=FieldByName('LongID').AsString;
สิ้นสุด; สิ้นสุด;
จบ;
รายการสิ้นสุดการอัปเดต;
จบ;
จบ;
---- ข้างต้นกล่าวถึงวิธีการพื้นฐานของการแสดงแผนผังฐานข้อมูล นอกจากนี้ เมื่อแก้ไขแอตทริบิวต์ข้อความของโหนดในแผนผังฐานข้อมูลจะถูกแก้ไขในเวลาเดียวกัน ผู้ใช้หลายรายในเวลาเดียวกัน ความสอดคล้องของฐานข้อมูลและทรี และทรี การคัดลอกและการจำลองโหนดบนจะไม่อธิบายโดยละเอียด และผู้อ่านสามารถปรับปรุงได้ด้วยตัวเอง
---- 2. การใช้การควบคุมไอพี
---- ในโปรแกรมเครือข่าย เรามักจะพบกับสถานการณ์ที่ผู้ใช้จำเป็นต้องป้อนที่อยู่ IP อย่างไรก็ตาม Delphi ไม่ได้จัดเตรียมการควบคุมที่สามารถใช้เพื่อป้อนสตริง IP ได้ ดังนั้นเราจึงต้องใช้ตัวควบคุม Tedit (กล่องข้อความบรรทัดเดียว) เพื่อยอมรับสตริง IP ที่ผู้ใช้ป้อน อย่างไรก็ตาม การใช้ Tedit เพื่อป้อนสตริง IP ไม่ใช่ความคิดที่ดี เนื่องจากไม่สะดวกในการจัดการ ในความเป็นจริง มีการควบคุม Windows อยู่ข้างๆ เราโดยเฉพาะสำหรับการป้อนสตริง IP ตัวควบคุม IP จะปฏิเสธสตริง IP ที่ไม่ถูกต้อง (สามารถป้อนได้เฉพาะตัวเลขระหว่าง 0..255 ในแต่ละส่วน) ซึ่งช่วยให้คุณได้รับค่า IP (จำนวนเต็ม 32 บิต) ที่สอดคล้องกับสตริง IP ในตัวควบคุมนี้ ช่วยคุณประหยัดปัญหาในการแปลงระหว่างสตริง IP และค่า IP นอกจากนี้ คุณยังสามารถจำกัดช่วงของ IP ที่สามารถป้อนในการควบคุม IP ได้อีกด้วย ในส่วนนี้จะแนะนำวิธีการใช้การควบคุม IP ของ Windows ในโปรแกรม Delphi ของเรา
---- มีไดนามิกลิงก์ไลบรารีที่สำคัญมากสองไลบรารีใน Windows: commctrl.dll และ comctl32.dll ซึ่งเป็นไลบรารีควบคุมแบบกำหนดเองของ Windows (Windows Common Controls) ไลบรารีการควบคุมแบบกำหนดเองประกอบด้วยตัวควบคุม Windows ที่ใช้กันทั่วไปมากมาย เช่น Statusbar, Coolbar, HotKey ฯลฯ ใน Delphi ตัวควบคุมเหล่านี้ส่วนใหญ่ได้รับการบรรจุเป็นตัวควบคุมแบบภาพ หลังจากที่ Microsoft เปิดตัว Internet Explorer 3 การควบคุมใหม่บางอย่างได้ถูกเพิ่มลงในไลบรารีการควบคุมแบบกำหนดเอง รวมถึงการควบคุม IP ของ Windows (การควบคุมการแก้ไขที่อยู่ IP)
---- 1. เริ่มต้นไลบรารีการควบคุมแบบกำหนดเองของ Windows
---- Windows มีฟังก์ชัน API สองฟังก์ชัน InitCommonControls และ InitCommonControlsEx สำหรับการเริ่มต้นไลบรารีการควบคุมแบบกำหนดเอง จากชื่อ จะเห็นความสัมพันธ์ระหว่างฟังก์ชัน API ทั้งสองนี้ไม่ใช่เรื่องยาก โดยฟังก์ชันหลังเป็นการเพิ่มประสิทธิภาพของฟังก์ชันแรก หากคุณต้องการใช้การควบคุม IP ในโปรแกรมของคุณ คุณต้องใช้ InitCommonControlsEx เพื่อดำเนินการเตรียมใช้งานไลบรารีและคลาสการควบคุมแบบกำหนดเองให้เสร็จสมบูรณ์ ต้นแบบของฟังก์ชัน InitCommonControlsEx มีดังนี้ (ไวยากรณ์ Pascal):
-
สร้างการควบคุม IP
-
ใช้การควบคุม IP ในโปรแกรมเราสื่อสารกับตัวควบคุม IP โดยการส่งข้อความถึงมัน
ตัวควบคุม IP สามารถตอบสนองหกข้อความต่อไปนี้และความหมายแสดงอยู่ในตารางด้านล่าง:
-
หากคุณต้องการได้รับค่า IP ที่สอดคล้องกับสตริง IP ในการควบคุม IP คุณควรส่ง
ข้อความ IPM_GETADDRESS และต้องการที่อยู่จำนวนเต็ม 32 บิตเป็น
พารามิเตอร์สุดท้ายของ SendMessage
-
---- 2. ข้อความแจ้งเตือนการควบคุม IP
---- เมื่อสตริง IP มีการเปลี่ยนแปลงหรือโฟกัสอินพุตถูกถ่ายโอน ตัวควบคุม IP จะส่งข้อความแจ้งเตือน IPN_FIELDCHANGED ไปยังหน้าต่างหลัก ในกรณีส่วนใหญ่ เราสามารถเพิกเฉยต่อข้อความแจ้งเตือนนี้ได้ ต่อไปนี้เป็นตัวอย่างของการจัดการข้อความแจ้งเตือน IPN_FIELDCHANGED:
ขั้นตอน Tform1.WndProc (var Msg: TMessage);
var p:PNMHDR;
เริ่ม
สืบทอด;
ถ้า Msg.Msg=WM_NOTIFY
จากนั้นเริ่มต้น
p:=ตัวชี้(Msg.lParam);
ถ้า p^.code=IPN_FIELDCHANGED
จากนั้นเริ่มต้น
-
การจัดการข้อความแจ้งเตือน IPN_FIELDCHANGED ของตัวควบคุม IP
-
จบ;
จบ;
จบ;
---- 3. วิธีการและการประยุกต์ใช้การควบคุมที่สร้างแบบไดนามิก
---- 1. สองวิธีในการสร้างการควบคุมใน Delphi
---- (1) สร้างการควบคุมในการออกแบบแบบฟอร์ม
---- เมื่อออกแบบฟอร์ม เป็นเรื่องปกติที่จะเลือกตัวควบคุมที่ต้องการโดยตรงในกล่องเครื่องมือควบคุม จากนั้นตั้งค่าคุณสมบัติและตอบสนองต่อเหตุการณ์
---- (2) สร้างการควบคุมแบบไดนามิกในโปรแกรม
---- บางครั้ง เราจำเป็นต้องสร้างการควบคุมแบบไดนามิกเมื่อโปรแกรมกำลังทำงานอยู่ ซึ่งมีข้อดีสองประการ: ประการแรก สามารถเพิ่มความยืดหยุ่นของโปรแกรม ประการที่สอง หากจำนวนการควบคุมที่สร้างขึ้นเกี่ยวข้องกับผลการรันระดับกลาง ของโปรแกรมเห็นได้ชัดว่าวิธีที่หนึ่งไม่สามารถรับรู้ได้และต้องใช้วิธีสร้างไดนามิกในโปรแกรม
---- วิธีการสร้างการควบคุมแบบไดนามิกในโปรแกรมแบ่งออกเป็นสามขั้นตอน ขั้นแรก กำหนดประเภทของการควบคุมที่สร้างขึ้น จากนั้นใช้ฟังก์ชัน Create เพื่อสร้างการควบคุม และสุดท้ายกำหนดค่าให้กับคุณสมบัติที่เกี่ยวข้องของ ควบคุม. การใช้ตัวควบคุม TButton เป็นตัวอย่าง ขั้นตอนมีดังนี้:
---- ก. กำหนดประเภทการควบคุม
var
Button1:Tปุ่ม;
---- ข. สร้างการควบคุม
Button1:=TButton.Create(ตนเอง);
Button1.Parent:=ตนเอง;
//โดยทั่วไป ให้ตั้งค่าการควบคุมพาเรนต์เป็นตนเอง หากไม่ได้ตั้งค่าพาเรนต์
จากนั้นการควบคุมจะไม่ปรากฏบนหน้าจอ
//แสดงมัน
---- c. ตั้งค่าคุณสมบัติอื่นๆ และกำหนดฟังก์ชันตอบสนองเหตุการณ์ที่เกี่ยวข้อง เช่น ฟังก์ชันคำอธิบายภาพ ซ้าย บน ความสูง ความกว้าง มองเห็นได้ เปิดใช้งาน คำแนะนำ และฟังก์ชันตอบสนองเหตุการณ์ onClick เป็นต้น
---- 2. การใช้วิธีการควบคุมที่สร้างขึ้นแบบไดนามิก
---- ในการพัฒนาระบบกำหนดเวลาการผลิตและระบบการจัดการ จำเป็นต้องสร้างแผนภูมิกำหนดการผลิตแบบไดนามิกซึ่งแสดงด้วยแผนภูมิแกนต์ และมีประโยชน์มากในการใช้การควบคุมรูปร่างเพื่อแสดงสถานะการประมวลผลของชิ้นส่วน (เวลาเริ่มต้นการประมวลผล) และเวลาสิ้นสุดของแต่ละกระบวนการ) เหมาะสม การใช้ตัวควบคุมแผนภูมิ การใช้อุปกรณ์การประมวลผลจะแสดงเป็นฮิสโตแกรมสามมิติ ซึ่งใช้งานง่ายมาก ตอนนี้เราจะอธิบายกระบวนการสร้างการควบคุมรูปร่างและการควบคุมแผนภูมิแบบไดนามิกในโปรแกรม
---- (1) สร้างการควบคุมรูปร่างแบบไดนามิกเพื่อแสดงแผนภูมิแผนการผลิต (แผนภูมิแกนต์)
ขั้นตอน TCreateMultiCharts.ProcCreateCharts;
var
i,j,แถว,คอลัมน์,RowSpace,ChartsHeight:จำนวนเต็ม;
ShapeChart:อาร์เรย์ของอาร์เรย์ของ TShape;
เริ่ม
Rows:=16; //จำนวนแถวในอาร์เรย์ควบคุมรูปร่าง
คอลัมน์:=8; //หมายเลขคอลัมน์อาร์เรย์ควบคุมรูปร่าง
RowSpace:=20; // ระยะห่างของแถวควบคุมรูปร่าง
ChartsHeight:=20; // ความสูงของการควบคุมรูปร่าง
SetLength(ShapeChart,แถว,คอลัมน์);
//กำหนดขนาดอาร์เรย์ ShapeChart
สำหรับ i:=0 ถึงแถวทำ
สำหรับ j:=0 ถึงคอลัมน์ทำ
เริ่ม
ShapeChart[i][j]:=TShape.Create(self);
ด้วย ShapeChart[i,j] do
เริ่ม
Parent:=Self; //บรรทัดนี้จำเป็น
มิฉะนั้น ตัวควบคุมรูปร่างจะไม่แสดงบนหน้าจอ
รูปร่าง:=stRectangle; // รูปร่างการควบคุมรูปร่างเป็นรูปสี่เหลี่ยมผืนผ้า
บนสุด:=45+i*(RowSpace+ChartsHeight);
ซ้าย:=รอบ(180+Q[i,j].เวลาเริ่มต้น);
//เนื่องจาก Q[i,j].StartTime เป็นจำนวนจริง จึงจำเป็นต้องปัดเศษ
ความกว้าง:=รอบ(Q[i,j].Value)
ความสูง:=แผนภูมิความสูง;
แปรงสี:=สีสุ่ม;
//ฟังก์ชันที่กำหนดเอง มีคำแนะนำแนบมาด้วย
Brush.Style:=bsSolid; //ตั้งค่าวิธีการเติม
เปิดใช้งาน:=จริง;
จบ;
จบ;
จบ;
---- หมายเหตุ: aQ เป็นอาร์เรย์สองมิติประเภทเร็กคอร์ด ซึ่งกำหนดไว้ดังนี้:
พิมพ์
TempData=บันทึก
ความคุ้มค่า:จริง;
เวลาเริ่มต้น: จริง;
จบ;
ถาม: อาร์เรย์ของอาร์เรย์ของ TempData
และส่วนประกอบของ Q ได้ถูกกำหนดค่าไปอีกกระบวนการหนึ่ง
---- ข. เพื่อแยกแยะส่วนต่างๆ รูปร่าง จะแสดงเป็นสีที่ต่างกัน ในขณะนี้ ฟังก์ชัน RandomColor ถูกเรียก ฟังก์ชันคือ:
ฟังก์ชั่น TCreateMultiCharts.RandomColor;
var
สีแดง สีเขียว สีฟ้า:ไบต์;
เริ่ม
สีแดง:=สุ่ม(255);
สีเขียว:=สุ่ม(255);
สีฟ้า:=สุ่ม(255);
ผลลัพธ์:=red หรือ (สีเขียว shl 8) หรือ (สีน้ำเงิน shl 16);
จบ;
---- (2) สร้างส่วนประกอบ ChartSeries ของตัวควบคุมแผนภูมิเพื่อแสดงการใช้งานอุปกรณ์แบบไดนามิก
ขั้นตอน TFormMultiMachinesBurthen.
ShowMachineBurthenCharts;
var
ฉัน:จำนวนเต็ม;
เบอร์เธน:จริง;
ซีรี่ส์คลาส:TChartSeriesClass;
NewSeries:อาร์เรย์ของ TChartSeries;
เริ่ม
SetLength(NewSeries,CreateMultiCharts.Rows);
MachinesBurthenCharts.height:=200;
MachinesBurthenCharts.Width:=550;
สำหรับ i:=0 ถึง CreateMultiCharts.Rows ทำ
เริ่ม
SeriesClass:=TBarSeries; //กำหนดรูปร่างเป็นแผนภูมิแท่งสามมิติ
NewSeries[i]:=SeriesClass.Create(Self);
NewSeries[i].ParentChart:=MachinesBurthenCharts;
NewSeries[i].เคลียร์;
Burthen:=เครื่องจักร Burthen[i];
Burthen:=Round(Burthen*100)/100; //ใช้เพียงตัวเลขสองหลักหลังจุดทศนิยมเท่านั้น
NewSeries[i].add(Burthen,',NewSeries[i].SeriesColor);
จบ;
จบ;
---- หมายเหตุ: (a).MachineBurthen[i] เป็นอาเรย์จริง ค่าของมันคือการใช้งานอุปกรณ์ที่เกี่ยวข้อง ซึ่งได้รับการคำนวณในฟังก์ชันอื่น;
---- (b) MachinesBurthenCharts เป็นตัวควบคุม TChart ตามที่อธิบายไว้ในส่วนประเภท
---- 3. โปรแกรมแสดงผลการทำงาน
---- (1) สร้างการควบคุมรูปร่างแบบไดนามิกเพื่อแสดงแผนการกำหนดเวลาชิ้นส่วน (ละไว้)
---- (2) สร้างส่วนประกอบ ChartSeries ของตัวควบคุมแผนภูมิแบบไดนามิกและแสดงการใช้งานอุปกรณ์ (ละไว้)