1

我正在尝试从 OPC 服务器获取标签列表,我正在使用 QuickOPC 中的 EasyDaClient。我想做的是这个

try
{
    //create the OPC Client object
    OpcLabs.EasyOpc.DataAccess.EasyDAClient easyDAClient1 = new OpcLabs.EasyOpc.DataAccess.EasyDAClient();

    //ServerDescriptor Declration
        OpcLabs.EasyOpc.ServerDescriptor sd = new OpcLabs.EasyOpc.ServerDescriptor();
sd.MachineName = "W7VM";
sd.ServerClass = "OPC.Siemens.XML.1";

    OpcLabs.EasyOpc.DataAccess.DANodeElementCollection allTags = easyDAClient1.BrowseLeaves(sd);

    foreach (OpcLabs.EasyOpc.DataAccess.DANodeElement tag in allTags)
    {
        //if the value is a branch add it to the listbox.
        if (tag.IsLeaf)
        {
            //add the fully qualified item id
            listBox1.Items.Add(tag.ItemId.ToString());
        }
    }


}
catch (Exception ex)
{
    MessageBox.Show("Error: " + ex.Message.ToString());
}

我总是从 BrowseLeaves 方法中获得 0 个元素,而且我不知道我的 Channel_1.Device_1 是什么,因此我可以使用其他重载。我是新手,有人可以解释一下如何列出 OPC 标签吗?仅供参考:我可以使用以下方法从标签中读取值:

easyDAClient1.ReadItem(MachineNameTextBox.Text,serverClassTextBox.Text,itemIdTextBox.Text);

所以它不是连接问题

4

1 回答 1

4

You are browsing the leaves at the root level, and there none there, that's why you get an empty collection.

What can you do? Several options there:

1) If you want to start the browsing at the root and get to the leaf level, you need to consider the branches as well. Use BrowseBranches method, or (maybe even better) use BrowseNodes, which returns both the branches and the leaves. When you get a branch node (you can test it using .IsBranch), you may decide to browse further into it.

2) If you want to get the leaves and know which branch they are at, you can pass in the branch name to the BrowseLeaves method as an additional parameter. However this is probably not your case, as I can guess form you saying "I don't know what is my Channel_1.Device_1 ", which is probably the branch ID that you do not "know" upfront.

Here is a complete example with recursive browsing:

// BrowseAndReadValues: Console application that recursively browses and displays the nodes in the OPC address space, and 
// attempts to read and display values of all OPC items it finds.

using System.Diagnostics;
using JetBrains.Annotations;
using OpcLabs.EasyOpc;
using OpcLabs.EasyOpc.DataAccess;
using System;

namespace BrowseAndReadValues
{
    class Program
    {
        const string ServerClass = "OPCLabs.KitServer.2";

        [NotNull]
        static readonly EasyDAClient Client = new EasyDAClient();

        static void BrowseAndReadFromNode([NotNull] string parentItemId)
        {
            // Obtain all node elements under parentItemId
            var nodeFilter = new DANodeFilter();    // no filtering whatsoever
            DANodeElementCollection nodeElementCollection = Client.BrowseNodes("", ServerClass, parentItemId, nodeFilter);
            // Remark: that BrowseNodes(...) may also throw OpcException; a production code should contain handling for it, here 
            // omitted for brevity.

            foreach (DANodeElement nodeElement in nodeElementCollection)
            {
                Debug.Assert(nodeElement != null);

                // If the node is a leaf, it might be possible to read from it
                if (nodeElement.IsLeaf)
                {
                    // Determine what the display - either the value read, or exception message in case of failure.
                    string display;
                    try
                    {
                        object value = Client.ReadItemValue("", ServerClass, nodeElement);
                        display = String.Format("{0}", value);
                    }
                    catch (OpcException exception)
                    {
                        display = String.Format("** {0} **", exception.GetBaseException().Message);
                    }

                    Console.WriteLine("{0} -> {1}", nodeElement.ItemId, display);
                }
                // If the node is not a leaf, just display its itemId
                else
                    Console.WriteLine("{0}", nodeElement.ItemId);

                // If the node is a branch, browse recursively into it.
                if (nodeElement.IsBranch &&
                    (nodeElement.ItemId != "SimulateEvents") /* this branch is too big for the purpose of this example */)
                    BrowseAndReadFromNode(nodeElement);
            }
        }

        static void Main()
        {
            Console.WriteLine("Browsing and reading values...");
            // Set timeout to only wait 1 second - default would be 1 minute to wait for good quality that may never come.
            Client.InstanceParameters.Timeouts.ReadItem = 1000;

            // Do the actual browsing and reading, starting from root of OPC address space (denoted by empty string for itemId)
            BrowseAndReadFromNode("");

            Console.WriteLine("Press Enter to continue...");
            Console.ReadLine();
        }
    }
}

Tech support: http://www.opclabs.com/forum/index

于 2014-08-07T06:59:01.097 回答