click tracking
April, 2008 - Katrien's MSDN Blog - Site Home - MSDN Blogs
Posts
  • Katrien's MSDN Blog

    Different ways for loading images and files in Silverlight 2 applications

    • 12 Comments

    When loading files in Silverlight 2 applications, this can range from images, video, fonts, etc, there are several options available. You might want to call files that reside on another server, files that are embedded into the .xap application or zip files that are downloaded and unpackaged on the client. In this post I’m reviewing the different options available for this, differences between them and how to implement each of the options.

    As an example to load the files I’m using a UserControl with an image on it. A very simple example that is clear enough to show the different approaches. All of the examples I'm showing here have a XAML based approach with a code based counterpart, except for the sample for on demand download.

    Base UserControl

    <UserControl x:Class="SLLoadResourcesApproaches.Page"
        xmlns="http://schemas.microsoft.com/client/2007" 
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
        <Grid x:Name="LayoutRoot" Background="White">
            <Image x:Name="imageElement" Stretch="Uniform" />
        </Grid>
    </UserControl>

    This just displays the image, nothing more:

    image 

    Referencing files in the same directory as the Silverlight application (ClientBin directory )

    In other words, this is the default location of your .xap file, so files that are located in the same directory as the base application. By default when you create the Silverlight application with a test web site in Visual Studio this is the ClientBin directory. No extra code is needed to load files in this location.

    If the file is placed in the ClientBin directory, call the file in XAML:

    <Image x:Name="imageElement" Stretch="Uniform" Source="_DTH8643.jpg" />

    Or in code:

    imageElement.Source = new BitmapImage(new Uri("_DTH8643.jpg", UriKind.Relative));

    Note: for the above sample you can use a forward-slash preceding the image name to express that it is located relative to the .xap file (same directory in this case). This is important to not as here it is not the root of the domain name (absolute path) that is taken into account. Take this example where I have a sub-directory to ClientBin, I’m referencing the file as /images/imagename.jpg.

    image

    To reference the file in the images directory in the ClientBin:

    imageElement.Source = new BitmapImage(new 
    Uri("/images/_DTH8643.jpg", UriKind.Relative));

    First time I used this it caused some confusion as I'm used to referrring to files in the root of the domain in this way, not in a sub-directory, so it's important to note this difference with Silverlight.

    Copying files to ClientBin upon build in Visual Studio

    In the case you are using the files directly in your Silverlight application and don't want to copy them manually to the ClientBin directory you can set this in Visual Studio. Note this is a copy to the ClientBin directory of the Silverlight application project, not the test web project you may have created.
    Build action: None.
    Copy to Output Directory: Copy always.

    image

    Loading files located outside of ClientBin (.xap location) directory

    In the above screenshot I have an image files located in the "images2" directory. To load images from that directory I can enter the full URL of the image:

    <Image x:Name="imageElement" Stretch="Uniform" 
    Source="http://localhost:55907/SLLoadResourcesApproaches_Web/
    images2/_DTH8643.jpg"
    />

    In C# code:

    imageElement.Source = new BitmapImage(
    new Uri("http://localhost:55907/SLLoadResourcesApproaches_Web
    /images2/_DTH8643.jpg"
    , UriKind.Absolute));

    Referencing files on external web sites

    If you want to call images that reside on external sites you can use the standard download method by using WebClient. Remember that cross domain restrictions apply.
    Other than that it is just like calling images using the full URL like above.

    imageElement.Source = new BitmapImage(new 
    Uri("http://farm3.static.flickr.com/2013/2438725399_4fa3c6eb2f.jpg?v=0", UriKind.Absolute));

    There is however maybe a better way to load a file in from an external site where you can better control the loading of your file before showing it in the UI. By using the WebClient class you can download external files on demand, be it from the current origin site or external sites (see below notes on cross domain restrictions). Using the WebClient you can control what to display while the image or file is being downloaded using event handlers. This approach however is not available in XAML but only in code.

    1. Create a WebClient object, an OpenReadCompleted event handler and start the download process

    WebClient webClientImgDownloader = new WebClient();
    webClientImgDownloader.OpenReadCompleted += new 
    OpenReadCompletedEventHandler(webClientImgDownloader_OpenReadCompleted); webClientImgDownloader.OpenReadAsync(photo);

    2. Set the source to the image in the OpenReadCompleted event handler

     void webClientImgDownloader_OpenReadCompleted(object sender, 
    OpenReadCompletedEventArgs e) { BitmapImage bitmap = new BitmapImage(); bitmap.SetSource(e.Result); imageElement.Source = bitmap; }

    Referencing files included in application package (the .xap file, not the assembly)

    When you need your Silverlight application to be independent of any files stored on the server separately you can include everything into a single .xap file. The same applies to file that are integral part of the application. If you know a certain file is always used when running the application it makes sense to include it in the .xap file as there is no reason to download it separately. Including files to be part of the package is what we call Content files.

    Files that are packaged into the .xap file need to have the Build Action in Visual Studio set to "Content".

    image

    To call the file from XAML:

    <Image x:Name="imageElement" Stretch="Uniform" Source="/_DTH8643.jpg" />

    Calling from code:

    imageElement.Source = new BitmapImage(new Uri("/_DTH8643.jpg", UriKind.Relative));

    Because the files is located at the same level in the application package as the assembly in which the code is running, the forward-slash preceding the name is required here as well.

    Files can also be located in sub-directories of the application package. You will notice that the directories are also included in the .xap file (as they would in any .zip archive file).

    Application resources: calling files embedded in the application assembly (DLL)

    As with other .NET assemblies, files can be embedded into the assembly as resources. For Silverlight applications, set the file Build Action to Resource.

    image

    Referencing resources embedded into the assembly is implemented in the same way as loading files included in the application (.xap). The difference is they are added to the DLL and thus no longer visible in the .xap file if you unzip it. 

    In XAML:

    <Image x:Name="imageElement" Stretch="Uniform" 
    Source="/_DTH8643.jpg" />

    Code call:

    imageElement.Source = new BitmapImage(new 
    Uri("/_DTH8643.jpg", UriKind.Relative));

    This is working well for the current assembly but if you want to use a file located in a referenced assembly (a Silverlight class library) you will need to add a special reference to indicate the assembly you are calling the file from. This is done by adding the following prefix to calling the file:
    /AssemblyName;component/

    So, in the example below I'm calling an image from the assembly named ReferencedSlLibrary.

    <Image x:Name="imageElement" Stretch="Uniform" 
    Source="/ReferencedSlLibrary;component/_DTH8643.jpg" />

    Code call:

    imageElement.Source = new BitmapImage(new 
    Uri("/ReferencedSlLibrarys;component/_DTH8643.jpg", UriKind.Relative));

    VS 2008 - SL 2 Beta 1 note: you will notice that the image does almost only get displayed in the Visual Studio designer if you set the source in the above manner, even for own assembly files. I'm guessing this is a bug in beta 1.

    Embedding fonts

    To embed fonts there is actually a specific implementation to call upon font files, see this great post by Tim Heuer on the different ways to do this.

  • Katrien's MSDN Blog

    Upcoming MSDN Evening sessions and user group presentations

    • 1 Comments

    May and June are busy months, as already posted VISUG is hosting the {Heroes Happen Here} Community Launch events but next to that there is more.

    MSDN Evening sessions

    All MSDN Evening sessions are planned to take place at the Utopolis in Mechelen.

    May 6: MSDN Evening: Developing an integrated e-commerce solution using Visual Studio, SQL Server and Dynamics CRM

    May 7: MSDN Evening: LINQ for Visual Basic 2008 Developers

    June 4: MSDN Evening: Building Windows Installer packages using XML and the WiX toolset

    June 11: MSDN Evening: Using Team Foundation Server for Version Control - Best Practices

    June 17: MSDN Evening: Mobile xRM - Combine the flexibility of Dynamics CRM with the power of Windows Mobile

    SQLUG session

    Thursday May 29, 2008 - "Managing, monitoring and troubleshooting SQL Server using Free tools" given by Dirk Gubbels (Microsoft)

    Abstract: Out of the box, SQL Server 2005 offers nice tools for managing and monitoring servers and databases. If you want to get an even richer experience and a broader toolset, there are a lot of hidden gems out there, free for you to download and to make the life of the DBA easier. This practical and demo-driven session will show you how to make best use of some of these. Topics include: Extending Management studio with custom reports, Performance dashboard, Sqlio, Dmvstats, RML Utilities and more...

    VISUG sessions

    VISUG is hosting 8 (yes 8!) {Heroes Happen Here} Community Launch events, and now an extra special session has been added with Ken Levy. Ken is community program manager on the Visual Studio Ecosystem team at Microsoft.

    VSX: Extend Your Visual Studio Development Experience - Tuesday, May 20, 2008
    Visual Studio provides a great set of development tools out of the box, and extending your platform with additional functionality brings you the benefits of the expanding VS ecosystem.

    Fasten your seat belt and get ready for a demo-centric roller coaster ride touring the end to end story around extending Visual Studio. From adding free or commercial extensions to VS like those found on our new http://visualstudiogallery.com web site, to building your own simple extensions for your own use, to distributing integrated packages to others for free, to creating a business or commercial product for VS developers, to innovating applications based on the new VS Shell royalty and license free. VSX, a shortcut name for Visual Studio Extensibility, represents the community which is a virtual and growing ecosystem that includes the VS SDK, all aspects of extending VS (packages, add-ins, macros, visualizers), .NET developers who extend VS, VSIP (Visual Studio Industry Partner) program companies, and the VS SDK team (also known as the VSX team or the VS Tools Ecosystem team).

  • Katrien's MSDN Blog

    Chopsticks Noodle: two new videos by Peter Himschoot

    • 0 Comments

    After Gregory Renard's "10 minutes with your RD" series, Peter Himschoot, also a Regional Director for Microsoft Belux has launched his series called "Chopsticks Noodle". The two first videos are now available on Chopsticks:

     

  • Katrien's MSDN Blog

    .NET Framework 3.5 Enhancements Training Kit (April Content Preview) available

    • 1 Comments

    The Visual Studio & .NET Framework evangelism team has just released the .NET Framework 3.5 Enhancements Training Kit. This is a preview containing 6 extensive labs on the following subjects:

    • ADO.NET Data Services
    • ADO.NET Entity Framework
    • ASP.NET AJAX History
    • ASP.NET Dynamic Data
    • ASP.NET MVC
    • ASP.NET Silverlight controls

    image

    Although the .NET 3.5 Extensions have not yet been released this will give you a jump start on the enhancements. New content will still be added (screencasts, demos, presentations) by the time .NET 3.5 Extensions RTM.

    Check out Jonathan's blog for more details.

  • Katrien's MSDN Blog

    MIX essentials micro blog

    • 2 Comments

    If you are a user of Twitter you may want to start following the MIX essentials micro blog. We are posting updates as they come available, so this is a good place to check for any new additions or information on the agenda.

    During the event on the 24th of April we will also be posting updates throughout the day, so check out http://twitter.com/mixessentialsbe.

    Also, if you are a Facebook user you can also add the event to your profile. And invite all your friends over as well: http://www.facebook.com/event.php?eid=25241388624. Don't forget that you still need to register over at the MIX essentials site as well :-)

     

    Technorati tags: ,,,

  • Katrien's MSDN Blog

    MIX essentials agenda update

    • 1 Comments

    We have just uploaded some changes to the MIX essentials agenda, as everything is now getting confirmed.

    In addition to the sessions that were already online when I first wrote on this event, new ones have been confirmed. And not to forget we have a very special guest for our closing keynote: Steve Ballmer.

    As you might have seen we have two separate tracks: developer and designer. When registering you can choose the track but this does not prevent you from changing tracks during the conference. 

    Developer track sessions

    Building RIAs with Silverlight 2 (Tim Heuer)
    Learn how to use Microsoft Visual Studio and Expression Blend to create Silverlight applications, how to create UI using XAML markup and code and how to customize the user experience to create unique experiences for your users.

    Developing with Windows Live (Catherine Heller)
    Learn how to build dynamic and interactive applications using the Windows Live platform. This session will cover APIs that enable streaming media, messaging and authentication

    Working with Data and Web Services in Microsoft Silverlight 2 (Gill Cleeren)
    Learn how easy it is to utilize POX, REST, RSS, ATOM, JSON, and SOAP in your Microsoft Silverlight mashup applications. Also learn how to easily access and display data with Silverlight using LINQ and databinding.

    Designer track sessions

    Digital Creativity - Now and the Future... (David Pugh-Jones)
    This session focuses on digital creativity and the evolution of advertising opportunities online now and in the future... explaining why advertisers need to re-think the way they communicate and reach out to consumers. Showcasing compelling and innovative rich media experiences including examples of collaboration with clients, agencies and creative, encompassing demonstrations of new and exciting Microsoft technologies including Silverlight and the next generation of video content online.

    Beauty & The Geek (Rich Griffin & Felix Corke, Conchango)
    The perfect blend of right brain and left brain
    In this session, you will see a real world team of a visual designer, whose primary world has traditionally been in Photoshop, Illustrator, Flash and HTML/CSS; and a developer, whose whole world has mostly been Visual Studio. These guys work at Conchango, one of Europe's leading web design agencies, on Silverlight & WPF projects, and have learned how the designer/developer story from Microsoft works in real life.
    In this session you'll get strategies, tools, tips on workflow and design approach with relevant real project case studies. Also, some useful snippets to get you started with Silverlight and DeepZoom, with Expression Suite and Visual Studio very quickly indeed.

    Virgins, Spaceships & Total Experience Design (Paul Dawson, Conchango)
    When was the last time you thought about touch, taste, or lighting when you designed a website? Experience Design must go wider than simply 'the Web' for any business. Using well known brands like Virgin and Harrods as case studies, you will learn how to create Experience Architectures that touch all customer interactions and how great offline customer experience can flow into digital media.

    Register before booking is closed!

    Technorati tags: ,,,

     

  • Katrien's MSDN Blog

    Silverlight and the HTML page: let your Silverlight do the work

    • 4 Comments

    One of the things I like with having Silverlight 2 runtime on the browser is that it gives us the power of .NET at the browser level. And this is more than just for creating RIAs, one aspect that does not get much attention is the fact that you can use the Silverlight plugin to have extra power at the browser level. With this I mean taking advantage of all the power of the .NET framework and your ease of work with C# to get things done in the browser.

    Even with the power of JavaScript debugging in Visual Studio 2008, if like me you are not a fan of lengthy applications in JavaScript this is a new possibility: just let Silverlight work with web services and processing and integrate that with your HTML page (DOM).

    You can use the Silverlight plugin without even visually showing it, if that would be a requirement. In this post I will show a few of the possibilities that you can use in your Silverlight classes to make them available to the hosting HTML page and even manipulate your page’s DOM from the Silverlight application.

    For this post I’m making a small demo application where an HTML page shows a list of thumbnails from Flickr photos together with the name. The call to Flickr is done by accessing Flickr’s REST API. What I’m doing is actually passing the calls that I would normally do using Ajax into the Silverlight application. As we all know it requires some work to get our Ajax working correctly in all browsers, with this approach we let Silverlight do the processing.

    Tools used: Visual Studio 2008 with the Silverlight 2 Beta 1 Tools for VS.

    Creating the Silverlight project

    Create a Silverlight Application project in Visual Studio. In my case I've named the application "FlickrPhotosSL". I've chosen to automatically create the web application as well as I'll be using the web application to create the HTML page in which to show the pictures. Everything is added to the default.aspx page that was created by Visual Studio in the web application. Please note that I'm using ASPX here but could as well be using a static HTML page. The advantage of using an ASP.NET is we can take advantage of the asp:Silverlight control.

    Accessing the DOM in Silverlight

    Because I don't want to display anything in the Silverlight control I'll just change the background to the color of the HTML page.
    Note: I did not find a way to completely hide the Silverlight plugin, will have to check how there is a better way to do this than setting a similar background. I tried setting the CSS class visibility to hidden but this causes the Silverlight plugin not to load anymore.

    <div id="test"></div>
    <div>
          <asp:Silverlight ID="Silverlight1" runat="server" 
    Source="~/ClientBin/FlickrPhotosSL.xap" Version="2.0" Width="10" Height="10" /> </div>

    Let's start with a small test to get a DIV from the Silverlight application and change its innerHTML. To do this the DIV is added to the HTML page, together with the Silverlight object:

    <UserControl x:Class="FlickrPhotosSL.Page"
        xmlns="http://schemas.microsoft.com/client/2007" 
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
        Width="0" Height="0">
        <Grid x:Name="LayoutRoot" Background="Transparent">
        </Grid>
    </UserControl>

    Then, in the Page.xaml.cs file we get a reference to the "test" DIV by calling HtmlPage.Document.GetElementById (lines 9 and 10).

       1:  public Page()
       2:  {
       3:          InitializeComponent();
       4:          this.Loaded += new RoutedEventHandler(Page_Loaded);
       5:   }
       6:   
       7:  void Page_Loaded(object sender, RoutedEventArgs e)
       8:  {
       9:          HtmlElement testDiv = HtmlPage.Document.GetElementById("test");
      10:          testDiv.SetAttribute("innerHTML", "Silverlight Page loaded");
      11:  }

    The result is the text being displayed when running the page. Nothing fancy here but that works.

    image

    Now we'll remove the code used for the test in the HTML page and Page.xaml.cs. Next we add a textbox in plain HTML together with a button. This will be our textbox to type in the Flickr tag name to search for. The objective is to have the onclick event of the button to fire code in the Silverlight application by calling a method made available to the browser.

    I'm also creating two DIVs: one for showing a list with pictures and another to be shown when the pictures are still loading.

    image

    Accessing Silverlight code from script

    In the Silverlight code we we need to make some changes to the Page class so the object and methods are available to the script. .NET objects can be made available by using HtmlPage.RegisterScriptableObject(). By default the members of the object are not available in the browser, so we need to add the attribute [ScriptableMember].

    So, we call RegisterScriptableObject in the page loaded and add a new method that will be called from script.

       1:  void Page_Loaded(object sender, RoutedEventArgs e)
       2:   {   
       3:         HtmlPage.RegisterScriptableObject("SilverlightFlickrObject", this);
       4:   
       5:   }
       6:   
       7:  [ScriptableMember]
       8:  public void SearchPictures(string tag)
       9:   {
      10:       ///code here
      11:   }

    In order to call the SearchPictures method from script we create a reference to the Silverlight plugin and call the method in JavaScript. The method is available because it has been decorated by the ScriptableMember attribute. The loadPicturesSilverlight function is called by the onclick event of the button.

    <script type="text/javascript">
         function loadPicturesSilverlight()
         {
             var slPlugin = document.getElementById("Xaml1"); //Silverlight plugin
             var searchTag = document.getElementById("textTag"); //textbox
               
             slPlugin.content.SilverlightFlickrObject.SearchPictures(searchTag.value);
         }    
    </script>
    Calling the Flickr REST service in Silverlight

    Now we only need to add code in Silverlight in order to search photos on Flickr and add them to the HTML page by generating HTML through Silverlight.

    Because we are accessing the Flickr REST API we'll use WebClient to make an asynchronous call to the Flickr service. This will return us an XML document that we can parse and read to print out the picture thumbnails in the HTML page. You'll want to download the whole sample to view the complete as I'm only showing the main parts hereunder.

       1:  [ScriptableMember]
       2:   public void SearchPictures(string tag)
       3:  {
       4:         WebClient rest = new WebClient();
       5:         rest.DownloadStringCompleted += new DownloadStringCompletedEventHandler
    (rest_DownloadStringCompleted);
       6:        rest.DownloadStringAsync(new Uri(string.Format(flickrApi, tag)));
       7:   }
       8:   
       9:   void rest_DownloadStringCompleted(object sender, DownloadStringCompletedEventArgs e)
      10:   {
      11:        string url = string.Empty;
      12:        string imageUrl = string.Empty;
      13:              
      14:        XDocument doc = XDocument.Parse(e.Result);
      15:   
      16:        HtmlElement ulList = HtmlPage.Document.CreateElement("ul");
      17:        picturesDiv.AppendChild(ulList); //pictures DIV
      18:   
      19:        picturesDiv.RemoveStyleAttribute("display");
      20:        picturesLoadingDiv.SetStyleAttribute("display", "block");
      21:   
      22:        picturesLoadingDiv.RemoveStyleAttribute("display");
      23:        picturesLoadingDiv.SetStyleAttribute("display", "none");
      24:   
      25:        var photos = (from results in doc.Descendants("photo")
      26:                 select new
      27:                  {
      28:                     PhotoId = results.Attribute("id").Value.ToString(),
      29:                     Farm = results.Attribute("farm").Value.ToString(),
      30:                     Server = results.Attribute("server").Value.ToString(),
      31:                     Secret = results.Attribute("secret").Value.ToString(),
      32:                     Title = results.Attribute("title").Value.ToString(),
      33:                     Owner = results.Attribute("owner").Value.ToString()
      34:                   }).Take(12);
      35:   
      36:      foreach (var photo in photos)
      37:      {
      38:        imageUrl = string.Format("http://farm{0}.static.flickr.com/
    {1}/{2}_{3}_m.jpg",
      39:                    photo.Farm, photo.Server, photo.PhotoId, photo.Secret);
      40:        url = string.Format("http://www.flickr.com/photos/{0}/{1}/", 
    photo.Owner, photo.PhotoId);
      41:                 
      42:        HtmlElement listItem = HtmlPage.Document.CreateElement("li");
      43:        listItem.SetAttribute("innerHTML", string.Format(LI_ITEM, url, 
    imageUrl, photo.Title));
      44:                     
      45:        ulList.AppendChild(listItem);
      46:      }
      47:   
      48:  }

    So the result is this, we type in a tag to search for:

    image

    And the result is retrieved by the Silverlight code that then adds new <LI> items to the page.

    image

    The sample code used in this post can be downloaded here:

    I can see some use for this in web applications that are currently using Ajax for this kind of processing and where there is no intention of transforming the whole interface into a Silverlight application. Using Silverlight in place of the Ajax calls could prove to be an advantage, especially if you already develop in C#.

    Reproducing my example using JavaScript and AJAX is possible, but it’s another approach to achieving the same results.

Page 1 of 1 (7 items)

April, 2008