Search code examples
c#wpfip-cameraonvif

Media & Device object or namespace could not be found


I am fairly new to c# and am trying to write a basic program to stream video via an Onvif camera device. I am able to mostly follow and understand this 8 min tutorial.

But a few things I can't figure out. Even after adding the Vlc references, and the two Onvif service reference there are a few pieces of the code that wont compile. The tutorial is difficult to follow because he skips major steps. I am trying to identify what Device & Media & EndPointAddress represent in the following code (per his tutorial).

public partial class MainWindow : Window
{
   UriBuilder deviceUri;
   Media.Media2Client media;
   Media.MediaProfile[] profiles;

   public MainWindow()
   {
      InitializeComponent();
   }


   private void button1_Click(object sender, EventArgs e)
   {
      //Constructor for the custom Uri requires the onvif service address. 
      deviceUri = new UriBuilder("http:/onvif/device_service");

      //Sting manipulation: Need to check if our address contains a port. (Input validation)
      string[] addr = Adress.Text.Split(':');

      deviceUri.Host = addr[0];

      if (addr.Length == 2)
         deviceUri.Port = Convert.ToInt16(addr[1]);

      System.ServiceModel.Channels.Binding binding;
      HttpTransportBindingElement httpTransport = new HttpTransportBindingElement();
      httpTransport.AuthenticationScheme = System.Net.AuthenticationSchemes.Digest;
      binding = new CustomBinding(new TextMessageEncodingBindingElement(MessageVersion.Soap12WSAddressing10, Encoding.UTF8), httpTransport);

      Device.DeviceClient device = new Device.DeviceClient(binding, new EndpointAddress(deviceUri.ToString()));
      Device.Service[] services = device.GetServices(false);

      Device.Service xmedia = services.FirstOrDefault(s => s.Namespace == "http://www.onvif.org/ver20.media/wsdl");

      if (xmedia != null)
      {
         media = new Media.Media2Client(binding, new EndPointAddress(deviceUri.ToString()));
         media.ClientCredentials.HttpDigest.ToString.ClientCredential.UserName = Login.Text;
         media.ClientCredentials.HttpDigest.ToString.ClientCredential.UserName = Login.Text;
         media.ClientCredentials.HttpDigest.AllowedImpresonationLevel = System.Security.Principal.TokenImpersonationLevel.Impersonation;

         profiles = media.GetProfiles(null, null);
         if (profiles != null)
            foreach (var p in profiles)
               listBox1.Items.Add(p.Name);

      }

      listBox1.SelectionChanged += OnSelectionChanged;
      video.MediaPlayer.VlcLibDirectoryneeded += MediaPlayer_VlcLibDirectoryNeeded;
      video.MediaPlayer.EndInit();


   }

   private void MediaPlayer_VlcLibDirectoryNeeded(object sender, Vlc.DotNet.Forms.VlcLibDirectoryNeededEventArgs e)
   {
      if (IntPtr.Size == 4)
      {
         e.VlcLibDirectory = new System.IO.DirectoryInfo(@"C:\Program Files\VideoLAN\VLC");
      }
   }

   private void OnSelectionChanged(object sender, RoutedEventArgs e)
   {
      if (profiles != null && listBox1.SelectedIndex >=)
      {
         UriBuilder uri = new UriBuilder(media.GetStreamUri("RtspOverHttp", profiles[listBox1.SelectedIndex].token));
         uri.Host = deviceUri.Host;
         uri.Port = deviceUri.Port;
         uri.Scheme = "rtsp";
         information.Text = uri.Path; ;
         string[] options = { ":rtsp-http", ":rtps-http-port=" + uri.Port, ":rtsp-user=" + Login.Text, ":rtsp-pwd=" + passwordBox.Password };

         video.MediaPlayer.Play(uri.Uri, options);

      }
   }
}

Solution

  • Both Device and Media are namespaces in your project with classes that are auto-generated from the web services that you have referenced. When you add a service reference via References > Add Service Reference, Visual Studio will create source code for a WCF client proxy from the WSDL metadata using the WCF Web Service Reference tool, so that can access that service.

    WSDL or Web Services Description Language is an XML based language for describing the interface of web services, you can find the ones from the tutorial here:

    The EndpointAddress class is located in the System.ServiceModel assembly, you probably got a typo there. However, there is also a NuGet package for it, called System.Private.ServiceModel, but you won't need that. From the documentation of EndpointAddress:

    Provides a unique network address that a client uses to communicate with a service endpoint.