Handling resizing in Adobe Air with HTML

If you develop a widget with Adobe AIR using HTML and Javascript, you may want to resize some elements of the HTML page depending on the size of the widget, thus having to resize them when the user decides to resize the widget. However, there’s a little trick on using the RESIZE event of the air.Event object.

The trick is that when the event is raised, and you execute some method on the corresponding event handler, the widget won’t have the correct size yet, so if you use the window.nativeWindow.width or window.nativeWindow.height values there you’ll be getting erroneus results.

The solution is quite easy, though. You just have to let the HTML engine to adjust everything he needs to sort out the new sizes and get those attributes after that. How do you do that? By putting your code in a setTimeout call with 0 milliseconds timer. Here you can find an example (assuming use of jQuery):

$(document).ready(function() {
    window.nativeWindow.addEventListener(air.Event.RESIZE, onResize);
});
 
function onResize() {
    var nativeWin = window.nativeWindow;
    setTimeout(function(){
    var width = nativeWin.width;
    var height = nativeWin.height;
    }, 0);
} //Here the values are correct

Share

Limiting the suggestions on jQueryUI Autocomplete widget

If you ever used autocomplete.ui plugin from jQuery UI and have an array with lots of suggestions you’ll see that the solutions provided by the plugin are not always satisfactory. You can add a scrollbar to the suggestions box by using a CSS hack, but even with that, you’ll have to render a big HTML that can be annoying on slow machines (mobile devices, for example).

I was working on a web site recently that had to be displayed on mobile devices and needed an autocomplete. But the suggestions array was big. A lot. This caused some problems on the mobile devices as they were behaving very slow, and the default plugin configuration doesn’t allow you to specify a maximum number of items to show in the suggesstions box.

So I decided to do a dirty hack into the plugin code to add this behaviour, adding a max property to the options to be able to limit the number of suggestions to show.

It’s not a perfect solution, because it should be implemented as a subclass or something, but if you need a fast solution, this is the way to go. You can find the code in my GitHub repository fork of jQueryUI. You can check the commit to see the changes I made.

Continue reading “Limiting the suggestions on jQueryUI Autocomplete widget” »

Share

jQuery Bars plugin

I was developing an application recently that needed some king of horizontal bars to be drawn on a web page. I found the jQuery Progressbar plugin and found it it was something similar to what I wanted to achieve, so I took some spare time and modified it to convert it in a plugin I could use in my app. The result is the jQuery Bars plugin. It’s a pretty simple plugin that will take a div and convert it into a horizontal bar, in which you can change the background color, the actual bar color, the duration of the animation and the height and width of the bar.

You can check a how it works and looks in this simple demo I just uploaded. It can be useful if you ever have to shown some kind of a percentage bar in a chart and you need a bit more customization that jQuery UI Progressbar gives you.

The plugin is dual licensed in MIT and GPLv2, the same license as jQuery, so feel free to use it or modify it at your will.

Share

Create your own JSONP Proxy using Ruby on Rails

Today I was working on a web site that needs to retrieve some RSS feed over the internet. Since the web page has no server (HTML + javascript only) I couldn’t access the feed from the server side. Also, because of the Cross Domain limitation of Ajax requests, I couldn’t access the RSS in the client either. I searched Google for an API and found the Google Feed API, which does exactly what I want. However, because (I think) Google caches the RSS feed you request, there was a significant delay (about half an hour) between the update of the RSS contents and the RSS provided by Google (the feed was updated in a per minute basis, as it was a CoverItLive event). Seeing I couldn’t access really recent posts from the feed using Google, I decided to implement my own RSS API using JSONP in a ruby on rails environment, since having an external server act as a proxy was allowed for the overall solution.

The tools I needed I got from those two websites: http://rubyrss.com/ for a RSS parser, and http://blogs.sitepoint.com/2006/10/05/json-p-output-with-rails/ on how to build a simple JSONP response on the server side.

Basically you have to start creating a new controller that will handle the JSONP requests. In my case I just added a ‘Feed’ controller:

$ script/generate controller Feed

Then you edit the app/controllers/feed_controller.rb file and start coding. We will assume that the request will come in this form: http://server/feed/get?callback=some_callback&url=the_url_of_the_feed. Having this information, the controller code is pretty straightforward.

class FeedController < ApplicationController
 
  require 'rss/1.0'
  require 'rss/2.0'
 
  def get
    begin
      url_contents = Net::HTTP.get(URI.parse(params[:url]))
      rss = RSS::Parser.parse(url_contents, false)
      json = { "error" => false, "feed" => rss }.to_json
    rescue
      json = { "error" => true }.to_json
    end
    respond_to do |format|
      format.js { render_json json }
    end
  end
 
  def render_json(json)
    callback = params[:callback]
    response = begin
      if callback
        "#{callback}(#{json});"
      else
        json
      end
    end
    render({:content_type => :js, :text => response})
  end
end

The first two lines are the requirements for the RSS module, which will allow us to parse a RSS feed. After that, we start with the get request. In there, we use the Net::HTTP.get() method, which will retrieve a URL content using a GET request and return its contents. To do so, we need to pass it an uri parameter, which we can get from the entire URL using the method URI.parse(). After this call, we have the XML of the RSS feed in url_contents. What we have to do now is build an RSS object with this XML. We’ll do that by calling RSS::Parser.parse(). If you wish to do some modifications to the RSS contents, now is your change. In this simple example we’ll simply bulk it all to the response.

To build the response, we need a JSON object. If everything went as expected, we can create a JSON object by simply creating a ruby associative array and calling the to_json method on it:

json = { "error" => false, "feed" => rss }.to_json

If, on the contrary, we got an error (bad URL, bad RSS, whatever), we simply return the same JSON object with the error property set to true (that’s done in the rescue clause).

After we have this JSON object built, we simply have to output the results. To do so, we use the help of a method called render_json which we have added to the controller code. In this method we simply output the JSON if we provide no callback (this means no JSONP), or either a padded JSON (hence the name JSONP) with the callback name followed by the JSON data. In either case we render the results as a js type.

For more detailed information on how JSONP works, check http://en.wikipedia.org/wiki/JSON#JSONP, but what you basically need to know is that when you do a JSONP request what you’re really doing is retrieve a chunk of javascript code that will be run on your client, so be aware of the security issues you can have here.

Share

Installing dropbox and dropbox-nautilus in ArchLinux

If you’ve tried to install dropbox-nautilus from the source found in the Dropbox website, you’ll find that you can’t successfully complete the ./configure step of the package due to an error of the script not finding pygtk. This is an issue with Archlinux because of the way python binaries are handled in this distribution. However, you can use the AUR packages to install dropbox and its integration with Nautilus thank to the people that tweaked the scripts to work with Arch.

The first step you have to take is download the AUR packages. You’ll need to download both dropbox and nautilus-dropbox. Save both .tar.gz files at you preferred location and uncompress them using this command:

tar xvfz <filename.tar.gz>

Obviously, change with the filenames you have downloaded. Each tar command will create a folder. Go to the dropbox folder and run this package:

makepkg -s

This will build a package and install the required dependencies while doing it if needed (it will ask for your root password if you’re doing this without being root). If everything went ok, you’ll find a file with the extension .xy in the folder you’re in. This is what you need to install, using our beloved pacman (use sudo if you’re not root):

pacman -U <filename.xy>

This will install dropbox. After this, do the same for the other package: nautilus-dropbox. makepkg -s, pacman -U <filaneme.xy> and you’re done, you have Dropbox integrated with Nautilus. Just start Dropbox from your Applications menu and enjoy the service!

Share

Routing a hiearchical path in ASP.NET MVC

If you wonder how to make a GitHub (and other websites) like routes to access to hierarchical paths or files, here’s the way to do it in ASP.NET MVC. GitHub is a GIT hosting service, and allows you to browse the repositories. When doing so, it uses a path as a routing parameter, as seen in this URL: https://github.com/erikzaadi/GithubSharp/blob/master/Core/Models/Commit.cs. This includes slashes and so to represent the directories, and is a parameter that depends on the file location inside the repository. A route like this can be done in ASP.NET using the called catch-all parameter.

The catch-all parameter allows you to use a wildcard on a route, so it takes everything after a given route as a single parameter. You can find the explanation of this feature in the ASP.NET Routing MASDN help page.

All you need to do to make a route like the one in the example to work is add this code to your Global.asax file, in the RegisterRoutes method:

routes.MapRoute(
    "Blob",
    "{*path}",
    new { controller = "Blob", action = "GetContents" }
);

This will pass the controller Blob a parameter called path that will contain the parameter you want (in the example that would be master/Core/Models/Commit.cs. All you have to do now is use this parameter as you wish so you can access the desired file and show it’s contents on a web page.

Share

Get the number of days in a month in .NET

If you’ve ever wondered how to get the number of days for a given month in .NET, the solution is pretty easy:

System.DateTime.DaysInMonth(int year, int month)

Hope it helps!

Share

Execute javascript code every time a form is loaded via Ajax.BeginForm

If you’ve ever used the Ajax.BeginForm code to render a form in ASP MVC using Ajax (via jQuery, for example), you may have wondered there’s an object you can pass to the call called AjaxOptions. This object allows you to pass the BeginForm call some interesting options to further enhance the form when it’s rendered. One of those options is specially useful if you want some javascript to be executed just after the form has been rendered. You can always use the $(document).ready in jQuery, but this code will not be called if, for example, the form is rendered after a postback and you have some validation errors (a missing required field, for example). Fortunately, you can use the AjaxOptions object to tell the form to execute a method right after the form has been loaded (for the first time or after a postback).

If you wonder how many parameters you can use in AjaxOptions you can visit the MSDN Help Page. The option we’re interested in in this post is OnSuccess. Take a look at this code:

<% using (Ajax.BeginForm("Action", "Controller", new AjaxOptions { UpdateTargetId = "someId", InsertionMode = InsertionMode.Replace, OnSuccess = "someFunction" }))
    {%>
        <%: Html.TextBoxFor(model => model.SomeProperty) %>
    <%}%>

This is a typical partial view that is intended to be used using an Ajax call. In it we simply display a TextBox to modify the property SomeProperty of our model. What we’re telling this form is that it should post to the Action action on the Controller controller. Everything is working as usual until here. However, we also pass the BeginForm an AjaxOptions object with some properties. The UpdateTargetId tells the form which DOM element on the page the form should be placed. The InserionMode tells the form what policy should follow when placing the form on the DOM, in this case we tell it that it should replace the contents of the element. And finally, OnSuccess tells the form what javascript code should execute once the form has been placed on the element, in this case we call a method called someFunction.

Imagine this is the HTML page in which we want to place this partial view:

<%@ Page Title="" Language="C#" Inherits="System.Web.Mvc.ViewPage<dynamic>" %>
<html>
<body>
    <div id="someId">
    </div>
</body>
</html>

We can then add this javascript script in the page:

$(document).ready( function {
    $.ajax({
        url: <%: Url.Action("Edit", "Controller" %>,
        success: function (data) {
            $('#someId').html(data);
        },
        error: function (XMLHttpRequest, textStatus, errorThrown) {
            jAlert('Some error message', 'Error');
        }
    });
});

What we’re doing here is loading via Ajax the Edit view using jQuery when the page loads. After the page has been loaded, then the Ajax.BeginForm call will look for a javascript method called someFunction and execute it. In there you can put whatever logic you need to be executed right after the form has been placed (for example, binding some elements to events or whatever). In this case, we can write a simple sample function like this one and add it on the partial view:

function someFunction() {
    alert('Form loaded');
}

Now each time the form is loaded via Ajax, or in a post, the alert will popup.

Share

Creating and consuming JSON data in MVC 2

Recently I started working in a project using MVC 2. I found out a very useful feature to retrieve JSON data from the server using an Action in a Controller.

This feature is in the base Controller class, which we inherit when we create a new controller. If you take a look into the different methods this class has you’ll find those ones:

//
// Summary:
//     Creates a System.Web.Mvc.JsonResult object that serializes the specified
//     object to JavaScript Object Notation (JSON).
//
// Parameters:
//   data:
//     The JavaScript object graph to serialize.
//
// Returns:
//     The JSON result object that serializes the specified object to JSON format.
//     The result object that is prepared by this method is written to the response
//     by the MVC framework when the object is executed.
protected internal JsonResult Json(object data);

Along with this method, there are some overloads that allow more parameters, you can see them all in here: Controller.Json Method. In this example I’ll use the first one, which is the simplest.

Continue reading “Creating and consuming JSON data in MVC 2” »

Share

C#, the “and” operators and lazy evaluation

Today at work we found a bug. My workmate, not used to C#, usually uses the & operator to compare boolean values. However, in C#, the & operator does not use lazy evaluation.

One curious thing about C# is that it can use two different operators to calculate an and expression: the & operator and the && operator. The difference between both is that the first one (&) can be used both with integer types and boolean types. When used with integer types it will perform a bitwise comparison between the two, and when used with boolean values it will use the logical and operation between the two boolean values, evaluating all the parts of the expression. This means that using a code like this one:

if (someObject != null & someObject.SomeProperty == someValue)

will throw a runtime error if someObject is null, because it will try to obtain the SomeProperty value.

However, the && operator is only available to boolean expressions, and it uses lazy evaluation, this is, if the first condition evaluated is false, it will calculate false without evaluating the rest of the expression, because an and is only true if all the expressions are true.

Conclusion, be sure to always use &amp& when evaluating boolean values if you want to avoid run time surprises :) .

Share