안녕하세요.
트리뷰를 가지고 작업하던중 질문을 하나 올립니다.
트리노드등의 data에 노드의 level에 따라 서로 다른 레코드형의 포인터가 들어 있습니다.
트리뷰의 change이벤트에서 data의 값을 가지고 작업하는데 노드마다 레코드형이 다르다보니 typecasting을 자동으로 할수 없습니다.
제가 알고싶은것은 클라스에 적용되는 is연산자처럼 레코드의 포인터를 식별하는 방법이 있는가 하는겁니다.
prec1=^trec1;
trec1=record
...
end;
prec2=^trec2;
trec2=record
...
end;
...
if vpointer is prec2 then ...
이런게 가능한가요?
기초가 없으니 매번 터무니없는 질문만 올리게되네요.
트리뷰 노드의 Data에 들어가는 레코드형에 레벨에 따라 동적으로 자료가 바뀌도록 형을 만들어서 사용하시는것이 좋을것 같네요...
아래와 같이 하시면 형변환이 거의 필요가 없어집니다.
레코드형대신에 객체를 만들어서 넣으시면 is연산자를 쓸 수 있지만... 좀 무겁죠...
type
// Level 0 데이터
PDataLevel0= ^TDataLevel0
TDataLevel0 = record
Field0: Integer;
end;
// Level 1 데이터
PDataLevel1 = ^TDataLevel1;
TDataLevel1 = record
Field1: Word;
end;
// Level 2 데이터
PDataLevel2 = ^TDataLevel2;
TDataLevel2 = record
Field2: Byte;
end;
// 노드에 실제 들어가는 레코드형
PNodeData = ^TNodeData;
TNodeData = record
case Level: Integer of
0: (Data0: TDataLevel0); // 정적인 TDataLevel0대신에 포인터인 PDataLevel0을 사용해도 됩니다.
1: (Data1: TDataLevel1); // 다만 포인터 관리만 잘 하시면...
2: (Data2: TDataLevel2);
end;
트리뷰의 노드에는 PNodeData를 넣으시고 노드에 있는 데이터의 식별은 PNodeData의 Level이란 필드로 검사하시면 쉽게 하실 수 있습니다.
begin
NodeData := PNodeData(TreeNode.Data);
case NodeData.Level of
0: NodeData.Field0 := 10; // Level 0일 때 처리
1: ...; // Level 1일 때 처리
2: ...; // Level 2일 때 처리
end;
혹은
if NodeData.Level = 0 then
... // Level 0일 때 처리
else if NodeData.Level = 1 then
... // Level 2일 때 처리
else if NodeData.Level = 2 then
...; // Level 2일 때 처리
end;