| Comments

i recently got an email from a developer who was using on a site to display high-quality media.  what?! you though silverlight was a windows-only technology? blasphemy!  you see, silverlight is a client-technology, which means as long as it can be served up to the browser (and the user has the plugin), the server can be your own custom version of l337hax0r web edition or whatever.  now, there are advantages of using internet information services on windows and some integration with asp.net, but that's not what this post is about.  on to the issue at hand will you...

so the email...he was getting an error message:

ActionController::RoutingError (No route matches "/player.xaml" with {:method=>:get}):

now i'm not incredibly familiar with what web server configuration he is running (although he is running netbeans/mongrel), but it got me thinking of 2 things.  first, maybe he needed to add a mime mapping.

for silverlight, the following MIME map is for .xaml files: .xaml: application/xaml+xml

but then i also thought that it might be something of some files moved around and such.  i deduced from his note that an template was being used as he mentioned he moved the javascript files to the javascripts directory of his rails application.  for those who don't know, rails is an MVC pattern web framework.  when creating a rails application you get a few different folders created for you (note: i'm just talking rails foo command here).  a lot of the work is done in controllers/models/views folder but there is also a folder called public.  within there are your typical images and javascripts type folders.  basically you can think of public mapping to "/" for static files.

now most rails applications probably wouldn't want all the encoder output to be dumped into /public as-is.  if developers are anything like me (OCD about project folder organization), then you want *.js to be in one place, etc.  i suspected that my reader put all the encoder files in the /public/javascripts folder.  this would be fine and should work okay.  but lets say you want some organization.

for example, i want to put my .js files in /public/javascripts, my jpg/pngs in /public/images and i'm going to create a folder for my xaml and a folder for media (wmv).  great, so we move all the files around then we run the Default.html page.  nothing happens.  why?  well a few things need to change if you move things around.

first, you need your hosting page (in this case right now it is Default.html) to reference the right path to the javascript locations.  so in our example we'd modify (in Default.html) lines like:

<script type='text/javascript' src="Silverlight.js"></script>
<script type='text/javascript' src="BasePlayer.js"></script>

to this:

<script type='text/javascript' src="javascripts/Silverlight.js"></script>
<script type='text/javascript' src="javascripts/BasePlayer.js"></script>

noting that of course there are more than just these two files.  now if we run the application it would still fail.  this is for two reasons, both of which are in StartPlayer.js.  the first is on or about line 8 of the script:

   4:  function get_mediainfo(mediainfoIndex) {
   5:      switch (mediainfoIndex) {        
   7:          case 0:
   8:              return  { "mediaUrl": "CodeTripSample.wmv",
   9:                        "placeholderImage": "CodeTripSample_Thumb.jpg",

the next is on or about line 24:

  22:  function StartPlayer_0(parentId) {
  23:      this._hostname = EePlayer.Player._getUniqueName("xamlHost");
  24:      Silverlight.createObjectEx( {   source: player.xaml', 

these both need to map to the right references of where that content has moved...so noting my above folder changes (images/javascripts/media/xaml) my StartPlayer.js file now starts like this:

   4:  function get_mediainfo(mediainfoIndex) {
   5:      switch (mediainfoIndex) {        
   7:          case 0:
   8:              return  { "mediaUrl": "media/CodeTripSample.wmv",
   9:                        "placeholderImage": "images/CodeTripSample_Thumb.jpg",
  10:                        "chapters": [               
  11:                                    ] };                                                                
  13:          default:
  14:               throw Error.invalidOperation("No such mediainfo");
  15:       }
  16:  }
  18:  function StartWithParent(parentId, appId) {
  19:      new StartPlayer_0(parentId);
  20:  }
  22:  function StartPlayer_0(parentId) {
  23:      this._hostname = EePlayer.Player._getUniqueName("xamlHost");
  24:      Silverlight.createObjectEx( {   source: 'xaml/player.xaml', 

and all is well -- my rails app starts and my silverlight content is loaded.  my resulting rails app structure looks like this:

simple enough, but if you move things around you might not have known where you need to change things.  you may wonder why you don't have to change the MediaElement in the player.xaml file.  well, if you are using an expression encoder template, the Url of that element is controlled by the StartPlayer.js mediaUrl attribute being passed to the player.

so if you have static information for your rails app this would probably work fine for you, but i suspect your rails application might be using views and such.  so you'd probably want to ensure you are modifying the appropriate view in views/layouts to ensure the javascript reference is correct, etc.

hope this helps.

Please enjoy some of these other recent posts...