如何在 LabVIEW 控件中显示数据
我有一个数值控件(不是指示器)和一个for循环(限制5)
我需要在数值控件中显示[数值控件中的当前循环索引+值]。我是 LabVIEW 新手。有什么想法可以做到这一点吗?
I have a numeric control( not Indicator) and a for loop(limit 5)
I need to display the [current loop Index+ value in the numeric control] in the Numeric control. I'm new to LabVIEW. Is there any idea to do this?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
要将值写入控件,您需要从中创建一个局部变量(右键单击程序框图上控件的接线端,然后选择“创建”>“局部变量”)。要让它更新 For 循环的每次迭代,请将局部变量终端放入 For 循环内,并将您想要显示的任何内容连接到该终端。我不确定这是否是一个好的用户界面设计,但它是您问题的答案。
您还可以使用局部变量从程序框图中的多个位置写入指示器,以及从指示器或控件中读取。对于任何给定的控件或指示器,可以有多个局部变量终端。每个局部变量终端都用于读取或写入 - 右键单击局部变量并选择更改为读取或更改为写入。
使用局部变量传递数据时应小心,因为程序流将不再像沿线路传递数据时那样受数据流控制,这可能会给您带来不可预测的行为(竞争条件)。如果读者只需要知道执行时的当前值,那么在一处写入并在多个地方读取是可以的,从多个地方写入指标也是如此,而指标仅用于向用户显示信息。
To write a value to a control, you need to create a local variable from it (right-click on the control's terminal on the block diagram and choose Create > Local Variable). To have it update each iteration of your For loop, put the local variable terminal inside the For loop and wire whatever you want displayed to that terminal. I'm not sure if this is going to be a good user interface design, but it's the answer to your question.
You can also use local variables to write to indicators from more than one place in your block diagram, and to read from indicators or controls. You can have more than one local variable terminal for any given control or indicator. Each local variable terminal is either for reading or writing - right-click on the local variable and choose Change to Read or Change to Write.
You should be careful about using local variables to pass data around, because program flow will no longer be controlled by data flow as it is when you pass data along a wire, and this could give you unpredictable behaviour (race conditions). Writing in one place and reading in multiple places is OK if the readers only need to know the current value at the time they execute, and so is writing to an indicator from multiple places where the indicator is only being used to display information to the user.
您需要经常更新控件有什么具体原因吗?
如果需要定期更新,最好将其更改为指示器。
如果您更新控件,用户通常会感觉自己不受“控制”。
Is there any specific reason you need to update a control that often?
If it needs to be updated that regular it might be better to alter it into an indicator.
If you update a control that often the user will have the feeling he's not in 'control'.
如前所述,您可以使用局部变量和属性节点来设置控件或指示器的值。如果您想持久保存数据,还有更好的方法。
谷歌“功能全局”或“labview 2风格全局”。基本模式是使用硬编码的 while 循环在一次迭代后停止。添加统一的移位寄存器。在循环内添加 case 结构。使用控件(布尔值、枚举或字符串)来选择案例结构。在您的 VI 上放置一对相同数据类型的控件/指示器。将指示器连接到环路外部右移位器的外部输出。将控件放在“set”(通常为 true,非默认)情况下的循环内部,并将其从情况中连接到右移位器的输入。转到其他空箱,并将左移位器的内部输出通过箱连接到连接到内部输入的端子。
因为您没有连接左移位器的外部输入,所以它是“统一的移位寄存器”。它将保留上次调用 VI 的数据。这就像在 ac 函数的堆上声明一个变量,并在下一个函数调用时使用最后分配的值。
三个主要好处是保留数据流、线程安全和性能。您可以通过向 VI 添加错误 IO 来获取数据流。由于VI的执行保证是原子的,所以线程安全得到保证。由于 LV 数据希望通过电线传输,因此性能得到了改善。每次将数据写入控件的属性节点时,LV 运行时都会将该数据写入 UI 线程。我认为当地人也有类似的基于线程的性能影响,但我不确定。
根据第一条评论...
为了您的利益从链接复制到这里(是的,读者先生)。
问题:
我正在考虑使用局部或全局变量;变量在哪个线程中执行?
解决方案:
一个常见的误解是局部和全局变量操作在 UI 线程中执行,或者需要线程交换到 UI 线程 - 这是不正确的。下面描述了局部和全局变量写入和读取操作的行为:
写入:
当写入局部或全局变量时,LabVIEW不会立即切换到用户界面线程。 LabVIEW 会将值写入传输缓冲区,该缓冲区是内存的受保护区域。用户界面将在下一个计划的更新时间更新。在发生单个线程切换或用户界面更新之前,可以多次更新变量。这是可能的,因为变量仅在执行线程中操作。
读:
当读取局部或全局变量时,该操作将发生在VI执行的线程中,因此,您可以通过将VI属性中的执行系统设置为标准来确保它不会发生在UI线程中。有一个线程保护机制可确保全局写入者在读取数据时不会更改数据,但这是通过互斥体完成的,而不是通过 UI 线程来完成。但是,如果打开了全局变量面板,则会发布一条消息来重绘全局控件,并且重绘将在 UI 线程中发生。
nekomatic是正确的。当您写入局部变量时,不会发生线程交换。
As mentioned aleady you can use local variables and proerty nodes to set the value of your control or indicator. If you are trying to persist data there is a much better way.
Google "functional global" or "labview 2 style global". The basic pattern is to use a while loop hard coded to stop after one iteration. Add an unitialized shift register. Add a case structure inside the loop. Use a control (boolean, enum, or string) to select on the case structure. Drop a control/indicator pair of the same datatype on your VI. Wire the indicator to the outter-output of the right shifter on the outside of the loop. Place the control INSIDE the loop in the "set" (usually true, non-default) case and wire it out of the case into the input of the right shifter. Go to the other empty case(s) and wire the inner-output of the left shifter through the cases to the terminal that connects to the inner-input.
Becuase you did not wire the outter-input of the left shifter it is an "unitialized shift register". It will persist data from the last call to the VI. This is like declaring a variable on the heap in a c function and having the last assigned value available to you at the next function call.
The three main benefits are preservation of data flow, thread saftey, and performance. You get data flow by adding error IO to your VI. Thread saftey is ensured becasue the VI's execution is guaranteed to be atomic. Perfomance is improved becasue LV data wants to live on a wire. Every time you write data to a control's proerty node the LV runtime writes that data to the UI thread. I think there is a similar threading based performance hit for locals too but I'm not sure.
Per the first comment...
Copied here from the link for your benefit (yes you Mr Reader).
Problem:
I am considering using local or global variables; in what thread do variables execute?
Solution:
A common misunderstanding is that local and global variable operations execute in the UI thread, or require a thread swap to the UI thread - this is not true. The following describes the behavior of local and global variable write and read operations:
Write:
When you write to a local or global variable, LabVIEW does not switch to the user interface thread immediately. LabVIEW instead writes the value to the transfer buffer, which is a protected area of memory. The user interface updates at the next scheduled update time. It is possible to update a variable multiple times before a single thread switch or user interface update occurs. This is possible because variables operate solely in the execution thread.
Read:
When you read from a local or global variable, the operation will occur in the thread which the VI executes, thus, you can be sure it does not occur in the UI thread by setting the execution system in the VI properties to standard. There is a thread protection mechanism to make sure that no writer of the global is changing the data while you are reading it, but this is done via a mutex, and not by going to the UI thread. However, if the global variable panel is opened, then a message is posted to redraw the global control, and the redraw will happen in the UI thread.
nekomatic is correct. The thread swap does not occur when you write to locals.
我同意托恩的观点。如果您以编程方式更改控件的值,那么您应该考虑它是否应该是一个指示器,或者可能有一个控件的伪指示器。
发布代码的独立版本是个好主意,这样我们就可以了解到底发生了什么。
I agree with Ton. If you are changing the value of a control programatically, then you should consider whether it should be an indicator, or maybe have a pseudo-indicator of the control.
It would be a good idea to post an isolated version of your code so we can understand what exactly is going on.
如果您想维护数据流来控制程序流,您可以使用控件的属性节点并设置“Value”属性。
要创建属性节点,请右键单击程序框图上控件的接线端,然后选择创建 » 属性节点 » 值。现在,您可以通过使用错误线来控制程序流来坚持数据流编程。
再次强调 Ton 的观点 - 如果您要经常更改控件的值,则可能值得将其更改为指示器。
If you wanted to maintain dataflow to control the program flow, you could instead use a property node of the control and set the "Value" property.
To create the property node, right click on the control's terminal on the block diagram, and select Create » Property Node » Value. Now you can adhere to dataflow programming by using error wires to control the flow of the program.
Again, to re-emphasize Ton's point - If you are going to change the value of a control frequently, it might be worth changing it into an indicator instead.