Adding Lync 2010 Features to Your Application (Part 2 of 2)

Summary:   This article introduces the Microsoft Lync 2010 API programmable types with a discussion of Lync 2010 API features and ease of programmability. Included is a sample C# class that demonstrates the simplicity of starting a Microsoft Lync 2010 conversation.

Applies to:   Microsoft Lync 2010 | Microsoft Lync Server 2010 | Published:   November 2010 | Provided by:   John Austin, Microsoft | About the Author

Contents

  • Lync 2010 API

  • Lync 2010 API Basic Features

  • Lync 2010 API Advanced Features

  • Lync Conversations

  • Code Example

  • Conclusion

Lync 2010 API

Your organization has previously installed Microsoft Lync Server 2010 and rolled out the Lync client to every workstation. Your IT department has provided everyone in the organization with a Lync-enabled USB phone and now everyone makes calls using the phone or the Lync client. You can use Lync to click a contact and start a conversation or you can dial a phone number to start a call… exactly like your old phone system. Your manager previously heard about the Microsoft Lync 2010 SDK and wants you to use it to integrate Lync phone calling into your line of business (LOB) application. You’re in the middle of a sprint to code an important new application module and you do not have much time to add a Lync feature.

With earlier COM-based communication APIs, you needed to schedule weeks of your time to build great communication features into your application. The task was easier if you were a C++ COM developer but a bit complex if you code in C# or Visual Basic .NET. The good news is that Lync 2010 API is a managed API. You can add Lync conversation features into your application together with several lines of code. What took weeks to code can now be done in a day, maybe less!

Lync 2010 API Basic Features

With Lync 2010 API, you can automate the starting of a Lync conversation window. Configure Lync to start a conversation with a Lync contact, SIP address, or any phone number that you select.

Conversation Modes

An automated Lync client conversation window hosts the conversation in either the instant messaging (IM) or audio/video modes. IM and video conversations are restricted to contacts or SIP addresses within your organization or with federated organizations. Audio calls can be placed to contacts or SIP addresses. Lync audio calls made to people outside your organization and federation use the public switched telephone network that is using the industry standard dialing pattern.

Transfer a file, share a desktop, program, or monitor in a Lync conversation window. By using only several additional conversation settings, you can easily share a running program, one of your monitors, or your complete desktop with the other participants in a Lync conversation. This feature is supported when all conversation participants are using Lync 2010.

Conversation Context

Add application context to any Lync conversation you start with Lync 2010 API. You can associate a new Lync conversation with a common application as long as that application can be installed on both your computer and the remote user’s computer. You can even pass application specific data in the conversation so all conversation participants can review the same application information during the conversation. This common application can be loaded into the Lync Conversation Window Extension and viewed by all conversation participants. This feature is supported when all conversation participants are using Lync 2010.

Conversation Window Docking

Dock a Lync conversation window inside your own application form. You can remove the frame from a Lync conversation window and then embed the conversation window inside a Microsoft Windows Forms or Microsoft Windows Presentation Foundation (WPF) page from your own application. If you write a bit of asynchronous event handling code by using Lync 2010 API, you can make your container form grow and shrink as the contained conversation window size changes.

Lync 2010 API Advanced Features

More advanced Lync features are available to you and require a little more programming experience:

  • Sign in to and out of Lync.

  • Publish your availability, out of office, and personal notes.

  • Get the availability of a contact, including their ability to accept different kinds of conversations.

  • Add and remove contacts from the Lync contact list.

  • Add, rename, or remove custom groupings of contacts.

  • Move contacts from one custom group to another.

  • Build your own contact list including custom and distribution groups.

  • Start new conversations or accept conversation invitations from other contacts.

  • Embed Lync instant message or audio/video feeds directly into your own application.

  • Hold, transfer or park Lync audio conversations.

Each of these advanced features will be discussed in a series of articles to be published over the coming months. If you are interested in tackling a fun Lync API coded project, stay tuned.

Lync Conversations

A single Lync conversation includes lots of functionality.

Conferencing

You can start a conversation with one other contact or many contacts at the same time. You can add more contacts to an ongoing conversation. Such multi-contact conversations are full-fledged conferences with many of the features of a conference hosted by the Lync client.

Conversation Modalities

A conversation started using Lync 2010 API can include the most popular modalities available with the Lync client:

  • Instant messaging

  • Audio

  • Video

  • Resource sharing (program, monitor, desktop)

  • File transfer

Audio Call Control

Audio call control is an advanced Lync 2010 API feature. This feature requires a basic understanding of asynchronous programming and event handling but it provides necessary call control support. To serve as a truly useful Lync-based software phone, your application should let a user hold a call, transfer a call to another Lync user or phone number, or park a call so that a colleague can pick it up. Lync 2010 API exposes all of these features using a straight-forward object model and a simple asynchronous coding pattern.

Conversation Context

One of the best Lync 2010 API features is that you can wrap a new Lync conversation in the specific context of your application and its data. In other words, you can configure an entry screen in your application (such as a user maintenance screen) so that any Lync call that you make from that screen can pass both the application ID of your application and application data such as a user ID to the colleague you call. By using these two pieces of information, the Lync client that is running on your colleague’s computer can start an instance of your application and provide enough information to open an appropriate entry form.

You can also create Microsoft Silverlight applications that are hosted within the Lync client. These Silverlight applications open in a Lync Conversation Window Extension and display exactly the application data that you want your colleague to see during your conversation.

The Real World

I have been talking about general Lync 2010 API features and hopefully you are somewhat excited about it by now. I said that Lync 2010 API was easy to code and now I am going to show you with a real-world example. In this example, I am going to start a Lync audio call with a customer by getting the customer phone number from an open customer maintenance screen in my accounting application and then pass that phone number together with a couple more pieces of information into a method I call on the Lync 2010 API Automation class.

In my example, I am running a Microsoft Dynamics Great Plains (GP) application that I have modified using the Dynamics GP Developer Toolkit. The code in the example is written in C# and responds to a button click on a customer maintenance form by making a Lync call using the customer phone number.

For this example to work, I must make sure that Lync is installed, running, and signed in on the computer executing this code.

Code Example

For the sake of simplicity, I have not included the code that obtains the customer maintenance form RMCustomerMaintenance object. What you should take from this example is that if you can obtain a phone number as a string from your application, you can make a Lync call. Step 4 in the following code gets a customer phone number from the customer maintenance screen of my GP accounting program.

Let me direct your attention to 7 tasks I achieve in this code:

  1. I added two Lync namespaces. Microsoft.Lync.Model and Microsoft.Lync.Model.Extensibility.

  2. I declared an instance of the Automation class.

  3. I declared and instantiated a Lync 2010 API enumeration (conversationModes) to specify that the new conversation is an audio conversation.

  4. I declared a Dictionary<AutomationModalitySettings, object> instance called conversationSettings so that I could further customize the conversation if it is necessary.

  5. I got the customer phone number from the GP customer maintenance screen (RMCustomerMaintenance.RmCustomerMaintenance.PhoneNumber1.Value) and added it to the list of conversation participants.

  6. I started the conversation using argument values set in steps 3 and 4.

  7. I handled an asynchronous callback event to end the start conversation operation. This step does not end the call, it finishes the call start operation.

I should emphasize that Lync 2010 API is primarily an asynchronous API and even the simplest operations include some form of asynchronous code. You can see from this example that I declared a very simple callback method and passed it into my BeginStartConversation call. This is only necessary because Lync 2010 API follows the conventional .NET asynchronous pattern of BeginOperation()/EndOperation calls. Although EndOperation calls can be made on the UI execution thread, you should use callback methods so that they can be called on the same worker thread that has started and completed an operation.

The following example shows how to use the BeginStartConversation method to launch a Lync conversation using a phone number string.

using System;
using System.Collections.Generic;
using System.Windows.Forms;
using Microsoft.Dexterity.Bridge;
using Microsoft.Dexterity.Applications;
using Microsoft.Dexterity.Shell;
using Microsoft.Dexterity.Applications.DynamicsDictionary;

//1: Add these namespaces.
using Microsoft.Lync.Model;
using Microsoft.Lync.Model.Extensibility;

namespace LyncCallSample
{
    public partial class LyncCall : DexUIForm
    {
        //2: Declare an Automation object.
        Microsoft.Lync.Model.Extensibility.Automation automation;

        public LyncCall()
        {
            InitializeComponent();
        }



        private void CallCustomer_Click(object sender, EventArgs e)
        {

            //3: Get the conversation modalities and settings.
            AutomationModalities conversationModes = AutomationModalities.Audio;

            //4: Declare and instantiate a dictionary of conversation settings.
            Dictionary<AutomationModalitySettings, object> conversationSettings =
                new Dictionary<AutomationModalitySettings, object>();


            if (automation != null)
            {
                //Get a participant.
                List<string> participants = new List<string>(1);

                // 5: Add the current customer to the conversation using the phone number on the customer maintenance form (RMCustomerMaintenance.RmCustomerMaintenance).
                participants.Add(RMCustomerMaintenance.RmCustomerMaintenance.PhoneNumber1.Value);
                try
                {

                    //6: Make the call.
                    automation.BeginStartConversation(conversationModes, participants, conversationSettings,
                                                      StartConversationCallback, null);
                }
                catch (LyncClientException lyncClientException)
                {
                    MessageBox.Show("Call failed.");
                }
            }
            else
            {
                MessageBox.Show("Lync was not initialized property.  Please restart this application.");
            }
        }

        /// <summary>
        /// Callback invoked when Automation.BeginStartConversation is completed
        /// </summary>
        /// <param name="result">The status of the asynchronous operation</param>
        private void StartConversationCallback(IAsyncResult result)
        {
            try
            {
                //7: End the start call operation.
                automation.EndStartConversation(result);
            }
            catch (LyncClientException lyncClientException)
            {
                MessageBox.Show("Call failed.");
             }
        }
    }
}

Conclusion

I hope I’ve whet your appetite to try Lync 2010 API. You can add communication functionality to your application with only several lines of code. By using Lync 2010 API, you can tightly integrate your new Lync client into your LOB application. The ability to start Lync conversations from your own application by using contact information straight from your entry screens is powerful. You can add Lync conversation and contact features into any application that loads managed code modules.

In a future article, I will show how to dock Lync conversation windows inside your own application so that they appear to be part of your own application. If you feel adventurous, stay tuned and I will show how to hide the whole Lync client interface and embed almost all of the Lync client functionality within your application.

About the Author

John Austin is a programmer/writer on the Microsoft Lync feature team. John has written several software development kits including Microsoft Office Communicator Web Access XML SDK, Microsoft Office Communicator 2007 Automation SDK, Microsoft Unified Communications Client Platform 1.0 SDK, and Microsoft Lync 2010 SDK.