status_t VariablesView::VariableTableModel::_AddNode(Variable* variable, ModelNode* parent, ValueNodeChild* nodeChild, bool isPresentationNode) { // Don't create nodes for unspecified types -- we can't get/show their // value anyway. Type* nodeChildRawType = nodeChild->GetType()->ResolveRawType(false); if (nodeChildRawType->Kind() == TYPE_UNSPECIFIED) return B_OK; ModelNode* node = new(std::nothrow) ModelNode(parent, variable, nodeChild, isPresentationNode); BReference<ModelNode> nodeReference(node, true); if (node == NULL || node->Init() != B_OK) return B_NO_MEMORY; int32 childIndex; if (parent != NULL) { childIndex = parent->CountChildren(); if (!parent->AddChild(node)) return B_NO_MEMORY; // the parent has a reference, now } else { childIndex = fNodes.CountItems(); if (!fNodes.AddItem(node)) return B_NO_MEMORY; nodeReference.Detach(); // the fNodes list has a reference, now } fNodeTable.Insert(node); // mark a compound type child of a address type parent hidden if (parent != NULL) { ValueNode* parentValueNode = parent->NodeChild()->Node(); if (parentValueNode != NULL && parentValueNode->GetType()->ResolveRawType(false)->Kind() == TYPE_ADDRESS && nodeChildRawType->Kind() == TYPE_COMPOUND) { node->SetHidden(true); } } // notify table model listeners if (!node->IsHidden()) { TreeTablePath path; if (parent == NULL || _GetTreePath(parent, path)) NotifyNodesAdded(path, childIndex, 1); } // if the node is hidden, add its children if (node->IsHidden()) _AddChildNodes(nodeChild); return B_OK; }
void VariablesView::TreeTableNodeExpandedChanged(TreeTable* table, const TreeTablePath& path, bool expanded) { if (expanded) { ModelNode* node = (ModelNode*)fVariableTableModel->NodeForPath(path); if (node == NULL) return; fVariableTableModel->NodeExpanded(node); // request the values of all children that don't have any yet // If the node only has a hidden child, directly load the child's // children's values. if (node->CountChildren() == 1) { ModelNode* child = node->ChildAt(0); if (child->IsHidden()) node = child; } // request the values for (int32 i = 0; ModelNode* child = node->ChildAt(i); i++) { if (child->IsPresentationNode()) continue; _RequestNodeValue(child); } } }
void* VariablesView::VariableTableModel::ChildAt(void* parent, int32 index) const { if (parent == this) return fNodes.ItemAt(index); // If the node only has a hidden child, pretend the node directly has the // child's children. ModelNode* modelNode = (ModelNode*)parent; int32 childCount = modelNode->CountChildren(); if (childCount == 1) { ModelNode* child = modelNode->ChildAt(0); if (child->IsHidden()) return child->ChildAt(index); } return modelNode->ChildAt(index); }
void VariablesView::VariableTableModel::NodeExpanded(ModelNode* node) { if (fContainer == NULL) return; AutoLocker<ValueNodeContainer> containerLocker(fContainer); // add children of all children // If the node only has a hidden child, add the child's children instead. if (node->CountChildren() == 1) { ModelNode* child = node->ChildAt(0); if (child->IsHidden()) node = child; } // add the children for (int32 i = 0; ModelNode* child = node->ChildAt(i); i++) _AddChildNodes(child->NodeChild()); }