OnNewText 事件后何时重绘 VirtualTreeView?

2024-04-15

我使用此代码来填充 VirtualStringTree 并允许重命名项目:

//---------------------------------------------------------------------------
// Structure for the tree
//---------------------------------------------------------------------------
struct TVSTdata
{
UnicodeString Name;
};
//---------------------------------------------------------------------------
// Initialization of the tree
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner) : TForm(Owner)
{
VirtualStringTree1->NodeDataSize = sizeof(TVSTdata);
// Fill all nodes with initial data
InitializeTree();
}
//---------------------------------------------------------------------------
// Fill all nodes with data and assign FocusedNode
//---------------------------------------------------------------------------
void TForm1::InitializeTree()
{
TVirtualNode* pNode;
TVirtualNode* pActiveNode;
TVSTdata*     pData;

VirtualStringTree1->BeginUpdate();
VirtualStringTree1->Clear();

pNode = VirtualStringTree1->AddChild(NULL); pData = static_cast<TVSTdata*>(VirtualStringTree1->GetNodeData(pNode)); pData->Name = "This is name 1";
pNode = VirtualStringTree1->AddChild(NULL); pData = static_cast<TVSTdata*>(VirtualStringTree1->GetNodeData(pNode)); pData->Name = "This is name 2";
pNode = VirtualStringTree1->AddChild(NULL); pData = static_cast<TVSTdata*>(VirtualStringTree1->GetNodeData(pNode)); pData->Name = "This is name 3"; pActiveNode = pNode;
pNode = VirtualStringTree1->AddChild(NULL); pData = static_cast<TVSTdata*>(VirtualStringTree1->GetNodeData(pNode)); pData->Name = "This is name 4";
pNode = VirtualStringTree1->AddChild(NULL); pData = static_cast<TVSTdata*>(VirtualStringTree1->GetNodeData(pNode)); pData->Name = "This is name 5";

VirtualStringTree1->Selected[pActiveNode] = true;
VirtualStringTree1->FocusedNode = pActiveNode; // PROBLEM -> if assigned from within OnNewText will still remain NULL and won't be set to pActiveNode!
VirtualStringTree1->EndUpdate();
}
//---------------------------------------------------------------------------
// Just display the text
//---------------------------------------------------------------------------
void __fastcall TForm1::VirtualStringTree1GetText(TBaseVirtualTree *Sender, PVirtualNode Node, TColumnIndex Column, TVSTTextType TextType, UnicodeString &CellText)
{
TVSTdata* pData = static_cast<TVSTdata*>(Sender->GetNodeData(Node));
CellText = pData->Name;
}
//---------------------------------------------------------------------------
// Allow editing
//---------------------------------------------------------------------------
void __fastcall TForm1::VirtualStringTree1Editing(TBaseVirtualTree *Sender, PVirtualNode Node, TColumnIndex Column, bool &Allowed)
{
Allowed = true;
}
//---------------------------------------------------------------------------
// Now this is where ideally I would reload the tree with new data - after rename
//---------------------------------------------------------------------------
void __fastcall TForm1::VirtualStringTree1NewText(TBaseVirtualTree *Sender, PVirtualNode Node, TColumnIndex Column, UnicodeString NewText)
{
NewText = "not important for this example as tree is reloaded anyway";
InitializeTree();  // ERROR is here - after assigning FocusedNode it is still NULL
//Timer1->Enabled = true; // If delayed call FocusedNode is correctly assigned and not NULL
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Timer1Timer(TObject *Sender)
{
//InitializeTree();
//Timer1->Enabled = false;
}
//---------------------------------------------------------------------------

问题 - when InitializeTree()最初被调用并且VirtualStringTree1->FocusedNode已分配 已正确分配(非 NULL)。

然而,如果这InitializeTree()函数被调用在OnNewText重命名事件后实际从数据库重新加载树 - 分配后FocusedNode它仍然是 NULL。所以显然树不能被重新加载和分配FocusedNode从内部OnNewText event.

我实现了延迟调用来重新加载新树并重新分配FocusedNode- 通过实现一个快速而肮脏的计时器(可以使用 PostMessage 来延迟函数调用,但这只是一个愚蠢的例子) - 在计时器内分配后,它不再为 NULL 并按预期工作。

任何人都可以指出我实现树重新加载的最佳方法是什么 - 比如使用可以安全设置新的特定事件FocusedNode并且它不会被重新分配回NULL?延迟函数调用是实现此目的的唯一方法还是有更好的事件可以捕获(例如,如果在OnNewText如果这个不允许设置焦点节点)。当然这可行,但我很感兴趣是否有更好的方法来做到这一点。


你无法改变FocusedNode当你在tsEditing树状态,直到你离开OnNewText事件,你就处于那种状态。这OnNewText本身更多的是用于编辑验证;这是一个事件,您可以在其中修改编辑的值。相反,你应该使用OnEdited编辑实际完成后触发的事件。因此,将数据库更新和树重新加载内容移至此处,如以下 C++ Builder 伪代码所示:

void __fastcall TForm1::VirtualStringTree1Edited(TBaseVirtualTree *Sender, 
  PVirtualNode Node, TColumnIndex Column)
{
  // update your database here; with VirtualStringTree1.Text[Node, Column] you
  // can access the current node text after edit; when you update your DB, call
  InitializeTree();
} 
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

OnNewText 事件后何时重绘 VirtualTreeView? 的相关文章

  • 以与文件大小相同的格式获取类或对象的大小?

    如何从内存中最好地确定类的大小 这是一个可以使用的基本示例类 请注意 这些变量除了用于示例之外没有其他用途 type TMyClass class public fString1 string fString2 string fIntege
  • Delphi LZMA减压样本

    我发现在this https stackoverflow com questions 4344976 lzma or 7zip in delphi的线程链接delphi压缩包 https github com ccy delphi zip具
  • C++ 中的静态虚函数

    我有一个基类和一个派生类 我想更改基函数 同时保持它们静态 因为它们应该作为静态传递给其他函数 我怎样才能做到这一点 ATL 框架通过将基类设为模板 然后让派生类将其类类型作为模板参数传递 从而绕过了无虚拟静态的限制 然后 基类可以在需要时
  • TControlState.csDesignerHide 与 TControlStyle.csNoDesignVisible

    VCL 似乎提供了两种向表单设计者隐藏控件的机制 TControlState csDesignerHide and TControlStyle csNoDesignVisible 就 IDE 而言 它们之间有什么区别 什么时候应该使用哪个
  • 如何修复 Delphi Prism ASP.NET 错误:“解析器错误消息:‘Oxygene’不是受支持的语言”

    我在 Delphi Prism 中编写了一个 ASP NET Web 应用程序 不是网站 在我的开发机器上一切正常 但是当我将其安装在测试服务器上时 出现以下错误 Server Error in MyApp Application Pars
  • iOS Objective-C 对象:何时使用release,何时不使用它

    我在 iOS 下 正在使用 delphi Tokyo 进行开发 这是我的代码 aUIImage TUIImage Wrap TUIImage alloc initWithCGImage aCGImageRef try aData TNSDa
  • 在 Outlook 中创建带有附件的邮件并显示它

    我想在 Outlook 中创建一封带有附件的邮件并在发送之前显示它 但我想我已经尝试了几乎在网上找到的所有示例 但没有任何运气 我可以使用 Indy 但我非常想使用 Outlook 来确保邮件正确 因为它是用于商业用途 函数的任何输入 该函
  • EIdOSSLUnderlyingCryptoError 和“使用 SSL 连接时出错。错误:14094410...”

    我在 OS X 上的 Delphi 10 1 Berlin 中遇到 Indy 组件问题 我正在使用TIdHTTP使用 HTTPS 连接到 Web 服务 问题是从 OS X 客户端连接到服务器 在 OS X 上运行时 我总是遇到同样的错误 P
  • 使用 StretchDIBits 使用 Delphi 6 处理条形码图像 - 输出中缺少条形线

    我的应用程序是在 Delphi 6 中开发的 由于后台处理和大量数据 它消耗大约 60MB 120MB 物理内存 这是一个资源密集型应用程序 该应用程序的功能之一是在进行某些处理后创建条形码图像 如果用户继续生成条形码 那么至少十分之一的条
  • Delphi - 将物理路径(设备文件句柄)转换为虚拟路径

    我怎样才能转换像这样的路径 设备 HarddiskVolume3 Windows 进入其相应的虚拟路径 如本例中的 c Windows 我个人更喜欢原生方式 function GetHDDDevicesWithDOSPath TString
  • Delphi 2007 中的 HelpInsight 文档

    我正在使用 D2007 并尝试使用 HelpInsight 功能 自 D2005 起提供 来记录我的源代码 我主要对让 HelpInsight 工具提示正常工作感兴趣 通过各种网上冲浪和实验 我发现了以下内容 使用三斜杠 注释样式比其他记录
  • 在 SQLite 数据库中存储日期时间值的最佳方式(Delphi)

    我将把日期时间值存储在 SQLite 数据库中 使用 Delphi 和 DISqlite 库 数据库的本质是它永远不需要在计算机或系统之间传输 因此互操作性不是一个限制 相反 我的重点是阅读速度 日期时间字段将被索引 我将对其进行大量搜索
  • 如何将 JSON 字符串转换为图像?

    我有一个将图像转换为 JSON 数组的应用程序 并将其保存到 blob 字段中 function getImage String var memorystream TMemoryStream jsonArray TJSONArray beg
  • 检测反射 DLL 注入

    在过去的几年中 恶意软件 以及一些渗透测试工具 如 Metasploit 的 meterpreter 负载 已经开始使用反射 DLL 注入 PDF http www harmonysecurity com files HS P005 Ref
  • Delphi中的抽象类

    我正在使用一个具有许多抽象类的组件套件 现在我想应用多态性 但在创建对象时收到错误抽象类 即使我不需要 我是否应该重写所有虚拟方法 有什么解决方法或解决方案吗 为了创建类的实例 您需要重写所有声明为虚拟抽象的方法 即使您不使用它们 如果您确
  • 如何向标准集合编辑器添加图标?

    我有一个自定义控件 它利用TCollection and TCollectionItem 在集合编辑器中 我想向每个列表项添加图标 该列表项由内部TImageList 在其父组件内 集合项本身代表图标 我想在这个编辑器中显示相应的图标 如何
  • 使用 TStringList 的分隔符解析字符串,似乎也解析空格(Delphi)

    我有一个简单的字符串 由某个字符分隔 比如说逗号 我应该能够创建一个 TStringList 并将其分隔符设置为逗号 然后将 DelimitedText 设置为我想要解析的文本 并且应该自动解析它 问题是 当我查看输出时 它还包含空格作为分
  • Delphi 5 的哈希表实现 [关闭]

    Closed 这个问题正在寻求书籍 工具 软件库等的推荐 不满足堆栈溢出指南 help closed questions 目前不接受答案 您知道 Delphi 5 的良好且免费的哈希表实现吗 我需要在哈希表中组织大量数据 并且我有点担心在网
  • 查找Delphi项目中的所有编译错误

    我正在对我的 Delphi 项目进行一些重构 我希望能够做出改变 然后看看all项目中因该更改而中断的地方 类似于 Eclipse 列出项目的所有编译错误 在 Java 中 在 Delphi 中 我可以进行更改 然后重新编译我的项目 但编译
  • 如何从 Delphi 中的函数返回对象而不导致访问冲突?

    我有一个返回 TStringList 的 delphi 函数 但是当我返回一个值并尝试使用它时 我收到一个访问冲突错误 即 myStringList FuncStringList myStringList Items Count lt Th

随机推荐