Showing posts with label HTML5. Show all posts
Showing posts with label HTML5. Show all posts

Thursday, October 9, 2014

Speech To Text Awesomeness in Siebel Open UI - Part 2

Welcome back to the second and final part of our speech to text tutorial (complete with awesome fonts).

In the first part, we created a custom PR for the Contact Form Applet and put all the Font Awesome files in the right places.

Today it's time to tackle the PR code in earnest. Remember we want to achieve the following:
So let's open our primordial physical renderer and implement the following code inside the ShowUI method:

Click to enlarge (yeah I know, it's just a screenshot)
Grab the full code here.

Let's walk through the code line by line:
  • First, we 'get' the GetControls property to initialize the controls variable with the current array of applet controls.
  • Then we obtain a handle on the JobTitle control as the JobTitleControl variable.
  • The if block helps us to verify that the JobTitle control exists and that the browser supports the HTML5 Speech Recognition API with this code:
    if (JobTitleControl && 'webkitSpeechRecognition' in window) {In case the window object does not 'know' of the webkitSpeechRecognition method, the code within the if block is not executed (i.e. nothing happens).
  • If we have speech recognition, we do the following:
    • Get the value of the name attribute of the JobTitle control (i.e. the Id) and use it to create a jQuery selector.
    • Create a new DIV element with the class attribute set to s2tbutton fa fa-microphone. The fa (Font Awesome) class is necessary that the DIV displays a microphone icon.
    • Now we create a webkitSpeechRecognition object using the line
      var recognition = new webkitSpeechRecognition();The object has various methods, one of which allow to set the code for the language to be interpreted. In our example we set recognition.lang="en-GB" to interpret the spoken text as British English.
    • Using the onresult event handler we can define a function that is invoked when the recognition process ends. But first let's stay outside this function as it is not invoked yet (this happens when a recording ends).
    • Next we add a custom class to the JobTitle control to allow custom styling.
    • Then we use the jQuery append method to add the button DIV to the control's parent element.
    • Finally we define a click event handler on the button which does two things:
      • Start the recognition (this will cause the browser to display an 'allow/deny' prompt to the user).
      • Toggle the button class to allow some animation.
    • Let's look back at the onresult event handler function and imagine that speech recognition has ended. Then we do the following:
      • Toggle the active class on the button (to end the animation)
      • Get the transcript (the recognized text) from the event object (quite a stretch)
      • Execute the SetFormattedValue method on the PM, passing the JobTitle control object and the recognized text as follows:
        that.GetPM().ExecuteMethod("SetFormattedValue", JobTitleControl, transcript);After consulting with fellow author Duncan Ford and the Siebel Open UI development team, this is the right way to "set a field value". The SetFormattedValue method triggers all the right spots in the framework. Remember, we should stay away from interacting directly with the BC.
      • The rest is just for fun and plays back the recognized text with a default synthesized voice:
        var msg = new SpeechSynthesisUtterance("Did you just say: " + transcript + "?");window.speechSynthesis.speak(msg);
As you see in the example code, there are some class references, so let's add the following CSS rules to a custom style sheet:

/* Text 2 Speech */
.s2tbutton {
    position: relative;
    right: 13px;
    top: 2px;
    font-size: 8pt;
    cursor: pointer;
}
.s2tbutton.active{
    text-shadow: 0px 0px 7px rgba(255,0,0,0.9);
    color: red;
    -webkit-animation: throbber 1s .165s infinite steps(3);
}
.s2tinput{
    width: 120px!important;
    text-transform: capitalize;
}

@-webkit-keyframes throbber {
    0%   {color: #000;}
    33%  {color: #f00;}
    100% {color: #000;}
}

The s2tbutton class controls the appearance of the idle microphone button.
The s2tbutton.active rule defines a red shadow and font color. Using the -webkit-animation property  we define a 'throbber' animation that has a 1 second duration and loops ad infinitum through three steps. The steps are defined using the webkit-keyframes "at-rule", so that the color goes from black to red and back. Thanks to Duncan for this cool animation.

The s2tinput class controls the appearance of the JobTitle control which we make a bit wider and apply capitalization to the text (because the speech recognition actually returns lowercase text).

Finally, let's fire up Google Chrome for a test.


The screenshot shows the Siebel client after clicking the microphone button (which is 'throbbing'). The browser prompts for allowance or denial.

Once we click the Allow button we can say the text, for example "Vice President"


A few moments after we stop speaking, the recognized text (not always exactly what you've said, but this time it's ok :) is set as the new field value.

Summary

What started as a simple demo with one line of code (that got deprecated) became a veritable journey into HTML5 speech recognition and synthesis. We added some (font) awesomeness to it by using a scalable icon which we animated with CSS.

For real life scenarios, I think that especially mobile users would benefit a lot from speech input, even more for longer text. It would also be interesting to explore all the options of the speech API such as allowing the user to select the spoken language or displaying the text as she or he speaks.


have a nice day

@lex

Monday, October 6, 2014

Speech To Text Awesomeness in Siebel Open UI - Part 1

If you have been following the various articles in the Siebel Open UI realm over the past two years you have probably seen a demonstration of speech recognition to provide field values via the device microphone.

The example code with this demo boils down to one line like this:

$('input[name="' + controlInputName + '"]').attr("x-webkit-speech","x-webkit-speech");

The above code is adding the x-webkit-speech attribute to a text input control so that we can simply click or tap a microphone icon and start speaking. Note that only Google Chrome supported this feature. Supported? Read on...

As you also probably know, this humble writer and his fellow authors are working on the Siebel Open UI Developer's Handbook (to be released early 2015). Of course, we aim to provide as many working examples as possible and the speech-to-text demo is something we have on our list.

However, while creating the demo code for the book we found to our dismay that the x-webkit-speech attribute is deprecated. Bummer...

HTML5 Rocks

This is where HTML5 (and any browser that supports it) comes to the rescue with the Speech Recognition (Web Speech) and Speech Synthesis API. Support for these APIs is currently limited to Google Chrome and Apple Safari browsers.

So we set out to give speech recognition in Siebel Open UI another chance and are happy to provide a working solution using the HTML5 APIs. In this and the following post we will describe how to use the following ingredients to create a custom physical renderer for a form applet:In 


Let's get started with a screenshot:


The highlighted microphone icon (in the Job Title control) is all the user can see. Tapping/clicking the icon will cause the browser (again: only Chrome or Safari support currently support this) to prompt the user that the web page wants access to the device microphone. After allowing that, the user can talk. Once she or he finishes talking, the field will be updated with the recognized text.

In the remainder of this first part we will lay out the foundation in terms of creating and registering a boilerplate PR and downloading the necessary files for Font Awesome.

1. Create and Register a Boilerplate PR

We assume a certain familiarity with Open UI at this point, so all we do here is create a new custom physical renderer file in the siebel/custom folder from a template.

  • We suggest that you name the file ContactSpeech2TextPR.js.
  • If you use the Siebel Essentials PR Template, continue by replacing all occurrences of 'PRTemplate' with 'ContactSpeech2TextPR'.
  • Next, ensure that the call to SiebelJS.Extend looks like the following to have a proper extension for a form applet:

SiebelJS.Extend(ContactSpeech2TextPR, SiebelAppFacade.PhysicalRenderer);

At this point, the PR does not do much apart from printing messages to the console (at least that's what our template does), but that's ok for now.

Next, we register the new file in the Manifest Files view:



Off we go to the Manifest Administration view and associate the file with the Contact Form Applet for the sake of demo.



Finally, log off and on again and verify that the PR is loaded (look at the JavaScript console for the log messages if you're using the Siebel Essentials template).

If you are already a Siebel Open UI veteran, you might well be annoyed by this level of detail here. Here at Siebel Essentials we aim to please juniors and seniors alike. So if you can't wait and want to jump ahead, here is the complete example PR (with full speech recognition and synthesis). Note that you also need Font Awesome files and some custom CSS, so reading on is recommendable.

Prepare for Font Awesome

Font Awesome is an open source icon and CSS toolkit which provides hundreds of vector icons. The benefit of using scalable font icons instead of image files becomes clear when you consider different zoom levels, the amount and size of files to be downloaded and whether you want to be old-school or just cool ;-)


For "ninja-style" testing you can include Font Awesome in any web page (including Open UI) with one line of JavaScript like the following:

$("head").append('<link href="//maxcdn.bootstrapcdn.com/font-awesome/4.2.0/css/font-awesome.min.css" rel="stylesheet">');

Of course the above will require that your browser can reach the public internet. For a real-life Siebel production environment, we will be better off if we download the source files and put it on our own Siebel web server. Here is how to accomplish this:

  1. Go to Fort Awesome and download the latest source archive.
  2. Open the archive and extract the font-awesome.css file to the PUBLIC/%Language%/FILES/custom folder. Do not use the minified version (some editing is necessary so we better use the original file).
  3. Create a FONTS folder in PUBLIC/%Language% (Note: This folder will be present in future Siebel versions, so you probably only have to do this only if you're on IP 2013).
  4. Create a custom sub-folder within the FONTS folder.
  5. From the Font Awesome archive, extract all font files to the PUBLIC/%Language%/FONTS/custom folder.
  6. Edit the font-awesome.css file and replace all occurrences of '../fonts/' with '../../fonts/custom/' to comply with the placement of files in the Siebel PUBLIC folder.
  7. Edit the custom theme.js file (that you hopefully have at this point, if not look here for a start on custom themes) and add a reference to the font-awesome.css file similar to the following example:

SiebelApp.ThemeManager.addResource(
    "TANGERINE_TAB",
    { css : {  fa: "files/custom/font-awesome.css"
        }}); 

Note that this applies to IP 2013. There is a high probability for future posts on custom themes in IP 2014...
Repeat the above step for any standard and custom theme you might be using.

Quite a stretch for a small icon but now we have the full power of Font Awesome at our fingertips.

Please also visit the next part where we will actually bring all the pieces together to capture your beautiful speaking voice in the Siebel database ;-)

have a nice day

@lex