Click here to Skip to main content
15,886,026 members
Articles / Web Development / ASP.NET

Blending HTML into Silverlight pages seamlessly

Rate me:
Please Sign up or sign in to vote.
4.42/5 (7 votes)
8 Feb 2009CPOL4 min read 62.7K   1.4K   40   5
This article will show a technique to blend an HTML page into a Silverlight page seamlessly through .NET/JavaScript interop and HTML frames.

Introduction

The scenario that this article solves is the following: I am developing a simple image viewer page with a menu on the top-left. The menu is developed using Silverlight. By clicking the menu button, users can view a resizable image on the main page. In addition to showing an image, I also want the main page to be able to show an HTML content. Moreover, I want to use a Silverlight control to show the image or the HTML content.

There are two issues to be solved:

  1. There is no existing HTML Silverlight control that can render an HTML page.
  2. How to route the OnClick event from the Menu control to the Image control.

In the following sections, I will show you an idea of solving the above problems.

I assume readers are familiar with ASP.NET/C#, Silverlight, Visual Studio, JavaScript, and DHTML.

Background

Calling a JavaScript function from .NET

Calling JavaScript from .NET code can be achieved through the HtmlPage.Window.Invoke(name, param object[] args) function of the System.Windows.Browser namespace.

Example of calling a JavaScript function Foo() from a C# function CallFooFromCSharp():

C#/Silverlight code:

C#
using System.Windows.Browser;

class FooClass
{
    public void CallFooFromCSharp()
    {
        HtmlPage.Window.Invoke("Foo", "Hello World");
    }
}

JavaScript code:

JavaScript
<script type="text/javascript">
function Foo(text) {
    alert(text);
}
</script>

Calling a .NET/Silverlight function from JavaScript

The converse to calling a JavaScript function from .NET can be achieved by first obtaining the Silverlight object and then calling the function using object.Content.[ObjectName].[FunctionName].

Example of calling a C# function Foo() from a JavaScript function CallFooFromJavascript():

C#/Silverlight code:

C#
using System.Windows.Browser;

class FooClass
{
    [ScriptableMember]
    public void Foo()
    {
        // do something
    }
}

JavaScript code:

JavaScript
<script type="text/javascript">
function CallFooFromJavascript() {
    var svlObject = document.getElementById("silverlightControl");
    svlObject.Content.FooClass.Foo();
}
</script>

Working with the HTML FrameSet

An important knowledge that we need to know about working with the FrameSet is how we:

  • Get a frame object:
  • C#
    var parentFrame = parent.frames['']
  • Calling a JavaScript function GetMainFrame() in the parent frame:
  • C#
    parent.GetMainFrame()
  • Calling a JavaScript function on one frame from a function in another frame:
  • C#
    var mainFrame = parent.GetMainFrame();
    mainFrame.Foo();

The code highlights

The HtmlSilverlightBlend.zip attachment contains three projects: ImageBrowser, MyMenu, and SilverlightInterFrameCommunication.Web.

  • The ImageBrowser project contains an ImageBrowser Silverlight control.
  • The MyMenu project contains a MyMenu Silverlight control.
  • The SilverlightInterFrameCommunication.Web contains a test web project with the index.html as the root page where the FrameSet is defined.

The following is the code snippet where the Silverlight menu button click is handled and routed to the JavaScript functions openImage() or openPage().

To show a Silverlight control that shows a particular image, the openImage() function will be called with the image URL specified. The idea is that we will call an ASPX page and pass an image URL as a 'tag' query string. The query string can be accessed from a Silverlight control by calling HtmlPage.Document.QueryString["tag"].

For example, I could pass the following to tell the ImageBrowser control to load an image with tag='A': ImageBrowser.aspx?tag=<A>.

The openPage() function will open a URL. It depends on what the URL value is and also the content served in that URL, but the point here is that you can load a normal HTML page with this approach.

MyMenu.Xaml.cs:

C#
private void Button_Click(object sender, RoutedEventArgs e)
{
    Button sourceBtn = (Button)sender;

   switch (sourceBtn.Name)
    {
        case "Obama":
            HtmlPage.Window.Invoke("openImage", "ImageBrowser.aspx", "obama");
            break;
        case "Gates":
            HtmlPage.Window.Invoke("openImage", "ImageBrowser.aspx", "gates");
            break;
        ...
        case "Microsoft":
            HtmlPage.Window.Invoke("openPage", "http://www.microsoft.com");
            break;
        case "Google":
            HtmlPage.Window.Invoke("openPage", "http://www.google.com");
            break;
    }
}

MyMenu.aspx:

JavaScript
function openImage(url, tag) {
    var imageUrl = url + "?tag=" + tag;

    // open imageUrl at mainFrame
    parent.OpenPage(imageUrl);
    parent.SetFooterCaption("My name is " + tag);
}

function openPage(url) {
    // open url at mainFrame
    parent.OpenPage(url);
    parent.SetFooterCaption("I am browsing " + url);
}

Points of interest

A different technique/discussion of blending an HTML page onto a page that has a Silverlight control has been reported in the Silverlight.net forums. One of the suggested hacky ways mentioned in the forum is to use the Opacity property of the Silverlight control (see below):

"Silverlight does not support hosting HTML (like WPF's Frame element), but that should not be a blocker. There's another way to achieve this. You position your HTML content directly under the Silverlight surface using DIVs. Then, declare the Silverlight plug-in (OBJECT tag) as transparent, plus set IsHitTestVisible="false" on the Silverlight elements. The transparency will ensure that HTML content shows through. You can have elements in Silverlight with opaque colors etc. That's fine. Then, the hit test visibility property ensures that mouse and keyboard events will pass through Silverlight into the HTML surface underneath."

- Ashish Shetty | Program Manager | Microsoft

In this article, we show a different way of solving the issue of blending HTML content with Silverlight content, that is using the .NET/JavaScript interop and the HTML FrameSet.

After reading this article, readers should now feel more comfortable about how the .NET/JavaScript interop works, and learn a technique to route an event from a Silverlight control to another Silverlight control. The example also shows how you can pass and process querystrings to a Silverlight control.

Your feedbacks/comments are appreciated. If you have a different idea of doing this, for example, a 1-page approach without using a FrameSet, let me know as I will be interested in learning your approach. The reason I am using this approach is that I have tried an approach of having more than one Silverlight control in an ASPX page and I found it was not trivial using a div/table to do the layout with more than one Silverlight control.

History

  • Initial version.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer
United States United States
Henry Tan was born in a small town, Sukabumi, Indonesia, on December 7th, 1979. He obtained his Bachelor of Computer System Engineering with first class honour from La Trobe University, VIC, Australia in 2003. During his undergraduate study, he was nominated as the most outstanding Honours Student in Computer Science. Additionally, he was the holder of 2003 ACS Student Award. After he finished his Honour year at La Trobe University, on August 2003, he continued his study pursuing his doctorate degree at UTS under supervision Prof. Tharam S. Dillon. He obtained his PhD on March 2008. His research interests include Data Mining, Computer Graphics, Game Programming, Neural Network, AI, and Software Development. On January 2006 he took the job offer from Microsoft Redmond, USA as a Software Design Engineer (SDE).


What he like most? Programming!Math!Physisc!Computer Graphics!Playing Game!

What programming language?
C/C++ but started to love C#.

Comments and Discussions

 
QuestionUnhandled exception 'script breakpoint' occurred in iexplore.exe Pin
Member 102564525-Sep-13 21:15
Member 102564525-Sep-13 21:15 
GeneralProblem with system.web.silverlight Pin
ponnasai6-Jul-10 0:45
ponnasai6-Jul-10 0:45 
GeneralGreat Article and Optional snippet Pin
Chesare28-Apr-10 3:13
professionalChesare28-Apr-10 3:13 
GeneralRe: Great Article and Optional snippet Pin
ponnasai6-Jul-10 0:25
ponnasai6-Jul-10 0:25 
GeneralExcellent article! Pin
csharp3r11-Jun-09 4:22
csharp3r11-Jun-09 4:22 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.