Haoran Blog  -  Stay hungry  Stay foolish

jQuery插件-Weather

今天在做有关jQuery的Weather的Widget, 查了很多有关weather的插件,基本上都用到了google的API 和yahoo的API, 具体如果引用还在学习中,到现在还没有在前台实现加入天气的插件,因此留下几个不错的Weather插件链接,接下来会选择一个比较容易实现的来做。

第一个weather插件转发

http://www.jqueryrain.com/?4EZzhY_j

And our widget will display weather similar to above one:

Our Weather Widget

What all things are needed to complete this widget?

  1. An html file for user interface
  2. jQuery library for AJAX request and DOM Manipulation
  3. Little knowledge about how YQL works

So how we are going to approach this?

We will first create an html page. The page contains a textbox to enter place name and a “Find Weather” button. Once user click the button, weather information is fetched using YQL, AJAX and displayed in a div.

What is YQL?

The Yahoo! Query Language is an expressive SQL-like language that lets you query, filter, and join data across Web services. With YQL, apps run faster with fewer lines of code and a smaller network footprint. You can read more about YQL here.

Now lets play with the code..

First of all we need an html file. Create an html file named ‘index.html’.

Add the following lines to <body> tag:

1
2
3
<input id="placename" />
<input id="findweather" value="Find weather" type="button" />
<hr />

We got an area to enter our placename. The UI now look like this.

Weather Textbox

Now next we need a container to hold our weather data. For that append the following html to <body> tag.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
<div id="weatherholder">
    <table id="weathertext">
        <tr>
            <td colspan="2" id="placetitle"></td>
        </tr>
        <tr>
            <td id="forecastimage">
                <img src="" id="weatherimage" />
            </td>
            <td id="statustext">
                <span id="temperature"></span><br/>
                <span id="condition" class="contents"></span><br/>
                <span id="dirspeed" class="contents"></span><br/>
                <span id="humidity" class="contents"></span>
            </td>
        </tr>
    </table>
</div>

I have put the ids for easy readablity. We need some styling for these elements. CSS will help us now. Copy the following css script inside <head> tag of our html file. It will take care of our basic styling.

1
2
3
4
5
6
7
8
<style>
    #weathertext{width: 250px; border: 1px solid #cccccc; display: none;}
    #placetitle{font-size: 36px; border-bottom: 1px solid #cccccc; text-transform: capitalize;}
    #temperature{font-family: arial; font-size: 24px; font-weight: bold;}
    .contents{font-family: arial; color: #999999; font-size: 12px; line-height: 20px;}
    #statustext{text-align: left;}
    #forecastimage{width: 120px;}
</style>

Now come, the core functionality part. First we will include the jquery reference using <script> tag. jQuery is a javascript file or javscript library which has ready made functions for usual tasks.

1
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js" type="text/javascript"></script>

Next inside a script tag paste the following javascript code.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
$(document).ready(function(){
    //binding click event for button
    $('#findweather').click(function(){
        $.getJSON('http://query.yahooapis.com/v1/public/yql?q=select%20*%20from%20weather.forecast%20where%20location%20in%20(%0A%20%20select%20id%20from%20weather.search%20where%20query%3D%22'+$('#placename').val()+'%22%0A)%20limit%201&amp;format=json&amp;diagnostics=true&amp;env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys&amp;callback=?',function(data){
            $('#weathertext').show();
            $('#placetitle').html($('#placename').val());
            $('#weatherimage').attr('src','images/'+data.query.results.channel.item.condition.code+'.png');
            $('#temperature').html(data.query.results.channel.item.condition.temp+' °F');
            $('#condition').html(data.query.results.channel.item.condition.text);
            var winddirection=parseInt(data.query.results.channel.wind.direction);
            var direction='';
            //finding wind direction
            switch(true)
            {
                case (winddirection==0):
                    direction='N';
                    break;
                case (winddirection&lt;90):
                    direction='NE';
                    break;
                case (winddirection==90):
                    direction='E';
                    break;
                case (winddirection&lt;180):
                    direction='SE';
                    break;
                case (winddirection==180):
                    direction='S';
                    break;
                case (winddirection&lt;270):
                    direction='SW';
                    break;
                case (winddirection==270):
                    direction='W';
                    break;
                case (winddirection&lt;360):
                    direction='NW';
                    break;
                case (winddirection==360):
                    direction='N';
                    break;
            }
            $('#dirspeed').html('Wind: '+direction+' at '+data.query.results.channel.wind.speed+' mph');
            $('#humidity').html('Humidity: '+data.query.results.channel.atmosphere.humidity+'%');
        });
    });
});

In our js code we have mainly used following jQuery Functions:

  1. .click() : what functionality has to be implemented when user clicks the button with id ‘findweather’
  2. $.getJSON : telling jQuery to fetch the response produced by given url and pass the response to ‘data’ parameter of callback function. .getJSON can be used only for fetching JSON response from a URL.
  3. .show() : show the specified hidden element
  4. .html(value) :  assign the html of given element with the value passed to .html function
  5. .attr(key,value): set the key of given element with given value

Also we have used parseInt() which is a javascript function which converts string to integer. This ensures data correctness while dealing with numerical calculations.

With these basic ideas in mind, look the code again. It basically takes the json data returned by getjson function and pick the needed values from data using data.key1.key2.value. If you have experience in object oriented programming, extracting data from json is similar to getting member variable values from objects.

Now you may be wondering, there is an image of sun or cloud in the screen shot. Is that image path also provided by our YQL. Not really. YQL returns a json data which contains weather condition. There are 47 types of weather conditions like cloudy, drizzle, windy etc. For each conditions there will be a number as you can see in the link provided.

 

第二个插件文章转发

How to Retrieve Yahoo! Weather using MagPie RSS and jQuery

Posted on December 10, 2008, under AJAXJavaScript

retrieve-yahoo-weatherretrieve-yahoo-weather

In this tutorial I will show you how to display the Yahoo! Weather on your website, using a PHP RSS Parser, called Magpie RSS and JQuery (AJAX). The Weather RSS Feed uses 2 parameters: ‘p’ for location & ‘u’ for degree units. The base URL for the Weather RSS Feed is http://weather.yahooapis.com/forecastrss. An address that gets the weather forecast in Sunnyvale, CA (zip code: 94089) in Celsius (c) looks like this: http://weather.yahooapis.com/forecastrss?p=94089&u=c.

Let’s start creating the necessary files for this script by starting with the html file here the JavaScript and CSS code will be called!

 

index.html

01.<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
02.<html>
03.<head>
04.<title>Yahoo Weather!</title>
05.<meta name="Keywords" content="ajax, weather, api, fetch, yahoo">
06.
07.<meta name="Description" content="yahoo, weather">
08.
09.<script type="text/javascript" src="jquery-1.2.6.min.js"></script>
10.
11.<link rel="stylesheet" type="text/css" href="style.css" />
12.
13.<script type="text/javascript">
14.<!--
15./*
16.Credits: Bit Repository
18.*/
19.
20.$(document).ready(function(){
21.
22.function get_weather()
23.{
24.var p = $("#code").val();
25.
26.var u = ($('#u').attr('checked')) ? '&u=c' : '';
27.var to_load = 'get_weather.php?p='+ p + u;
28.
29.$("#weather").show();
30.
31.$("#weather").html('<img style="margin-top: 104px;" src="ajax-loader.gif" align="absmiddle">');
32.
33.$("#weather").load(to_load);
34.}
35.
36.// Trigger "get_weather" when the window loads
37.$(window).load(get_weather);
38.
39.// Trigger "get_weather" when the form objects are used
40.$("#code").change(get_weather);
41.$("#u").click(get_weather);
42.});
43.
44.//-->
45.
46.</script>
47.
48.</head>
49.
50.<body>
51.<center>
52.
53.<div align="center">
54.
55.<h2 align="center">Yahoo! Weather</h2>
56.
57.<form>
58.Get Weather for: <select id="code" name="code">
59.<option value="USCA1116">Sunnyvale</option>
60.
61.<option value="USNY0996">New York City</option>
62.<option value="FRXX0076">Paris, France</option>
63.<option value="UKXX0085">London, United Kingdom</option>
64.<option value="UKXX0687">Buckingham, United Kingdom</option>
65.
66.<option value="ASXX0001">Adelaide, Australia</option>
67.</select>
68.
69.<input type="checkbox" id="u" name="u" value="c">&nbsp;with degrees Celsius and other metric units
70.
71.</form>
72.
73.<div id="weather"></div>
74.</div>
75.</center>
76.</body>
77.</html>

style.css

01./*
02.Credits: Bit Repository
04.*/
05.
06.html, body
07.{
08.padding0;
09.border0px none;
10.font-size12px;
11.font-familyVerdana;
12.}
13.
14.table
15.{
16.font-size12px;
17.font-familyVerdana;
18.}
19.
20./* Input */
21.input, select, checkbox
22.{
23.margin5 5 5 0;
24.padding2px;
25.
26.border1px solid #999999;
27.border-top-color#CCCCCC;
28.border-left-color#CCCCCC;
29.
30.color#333333;
31.
32.font-size13px;
33.-moz-border-radius: 3px;
34.}
35.
36.#weather
37.{
38.border1px solid #cccccc;
39.-moz-border-radius: 3px;
40.
41.width500px;
42.
43.padding5px;
44.
45.height240px;
46.}

Let’s analyze the JS code! After $(document).ready() is called, the get_weather() function is created. It is used to pass the data from the form to get_weather.php using AJAX. This function is triggered when the page loads

1.$(window).load(get_weather);

and when either the select or checkbox form objects are used

1.$("#code, #u").change(get_weather);

.

We need to determine the value of the selected location from the form. Here’s the code that does this:

1.var p = $("#code").val();

Did the user choose to see the weather with degress Celsius and other metric units? We have to determine if he checked the checkbox:

1.var u = ($('#u').attr('checked')) ? '&u=c' '';

What we will load?

1.var to_load = 'get_weather.php?p='+ p + u;

The parameters passed are ‘p’ (which is required) and u (if it’s requested). Using AJAX, a call is made to get_weather.php. Until the data is retrieved, an animated GIF loader is showing up:

1.$("#weather").html('<img style=""margin-top:" 104px;"="" src=""ajax-loader.gif"" align=""absmiddle"/">');
2.$("#weather").load(to_load);

Here’s the content of get_weather.php, the file that connects to Yahoo! and gets the weather forecast:

01.<?php
02.error_reporting (E_ALL ^ E_NOTICE);
03.
04.if(isSet($_GET['p'])) // at least 'p' is required
05.{
06.$p $_GET['p'];
07.
08.$u = isSet($_GET['u']) ? $_GET['u'] : '';
09.
10.require('magpierss/rss_fetch.inc');
11.
13.
14.$rss = fetch_rss($url);
15.
16.$title $rss->items[0]['title'];
17.
18.$description $rss->items[0]['description'];
19.
20.echo "<br />".$title."<br /><br />".$description."<br />";
21.}
22.?>

 

yahoo-weather-magpie-rss-jqueryyahoo-weather-magpie-rss-jquery

 

After we hide any notice errors using error_reporting (E_ALL ^ E_NOTICE);, we have to determine if the parameter ‘p’ is requested or not. If it is, we’ll check if the ‘u’ parameter was requested too and use we call the function fetch_rss() passing the $url to it. The function will return an array containing the data parsed from the RSS Feed. I chose to show ‘title’ and ‘description’:

1.$rss = fetch_rss($url);
2.
3.$title $rss->items[0]['title'];
4.$description $rss->items[0]['description'];
5.
6.echo "<br />".$title."<br /><br />".$description."<br />";

To see all the values of the array use the following code:

1.echo "<pre>"; print_r($rss); echo "</pre>";

If you need to find the codes for specific locations go tohttp://weather.yahoo.com/.

NOTE: The PHP Parser, MagPie RSS, caches the data retrieved from the feed. This is useful to load the data faster the next time you use the script. The default caching time is one hour (of course you can modify it). Consider checking the documentation files from the ‘magpierss’ folder (in the attached zip) for more information.

I hope that this tutorial gave you an idea of how to retrieve data from RSS using PHP & AJAX. If you have any comments regarding this article, please post them.

Happy coding 😉

 

第三个weather的插件转发

http://www.jqueryrain.com/?JiCuxN4C

A simple jQuery plugin to display the current weather information for any location using Yahoo! Weather. Developed by James Fleeting.

Download v2.2.0

Last updated on April 30, 2013

bower install jquery-simpleweather

 


Introducing simpleWeather

Check out the original demo on codepen.


Example Usage

The demo above gives you a real world example of how to display and style the weather. The table below shows every piece of data that is available for you to use. In most cases you won’t need the majority of it however I make it all available so you can use whatever you want. The example values with links (thumbnail, image, link) all return the url, I just linked it so the table didn’t look cluttered.

Data Description Example value
title Returns the generic title for the weather being displayed. Conditions for Austin, TX at 2:50 pm CST
temp Returns current temperature for selected location without unit. 75
tempAlt If unit is set to f (fahrenheit), this will return the current temp in c (celsius) or or vice versa. 24
code Returns the current condition code. View a list condition codes. 32
todayCode Returns the condition code for the day vs current. View a listcondition codes. 30
units.temp Returns the unit in which temp is displayed, f for Fahrenheit or c for Celsius. This can be changed when calling simpleWeather. f
units.distance Returns the unit in which distance is displayed, mi for miles or km for kilometers. mi
units.pressure Returns the units of barometric pressure, in for pounds per square inch or mb for millibars. in
units.speed Returns the unit in which speed is displayed, mph for miles per hour or kph for kilometers per hour. mph
units.tempAlt Returns the opposite from units.temp (if Fahrenheit, this will return the temp in Celsuis). c
currently Returns a textual description of the current condition. Partly Cloudy
high Returns the forecasted high temp for the day. 82
highAlt Returns the opposite from high (if Fahrenheit, this will return the temp in Celsuis). 28
low Returns the forecasted low temp for the day. 47
lowAlt Returns the opposite from low (if Fahrenheit, this will return the temp in Celsuis). 8
forecast Returns a textual description of the condition for the day vs current. Sunny
wind.chill Returns the current wind chill in degrees. 71
wind.direction Returns the current wind direction. NW
wind.speed Returns the current wind speed. Use with units.speed to display mph or kph. 13
humidity Returns current humidity in precent. 63
heatindex Returns the current heatindex. 71
pressure 29.85
rising Returns the state of the barometric pressure; steady (0), rising (1), or falling (2). 0
visibility Returns current visibility in distance. Use with units.distance for mi or km. 10
sunrise Returns the time of sunrise for today. 7:26am
sunset Returns the time of sunset for today. 5:47pm
thumbnail Returns the thumbnail image url for the current condition code and time of day. View Image
image Returns the full size image url for the current condition code and time of day. View Image
tomorrow.high Returns the forecasted high temp for tomorrow. 78
tomorrow.highAlt Returns the opposite from tomorrow.high (if Fahrenheit, this will return the temp in Celsuis). 25
tomorrow.low Returns the forecasted low temp for tomorrow. 41
tomorrow.lowAlt Returns the opposite from tomorrow.low (if Fahrenheit, this will return the temp in Celsuis). 5
tomorrow.forecast Returns a textual description of the condition for tomorrow. Thunderstorms
tomorrow.code Returns the condition code for tomorrow. View a list condition codes. 4
tomorrow.date Returns the date for tomorrow. 12 Jan 2013
tomorrow.day Returns the day for tomorrow. Sat
tomorrow.image Returns the full size image url for tomorrow’s condition code and time of day. View Image
city Returns the city name. Austin
country Returns the two character country code. US
region Returns the state, territory, or region. TX
updated Returns when the weather feed was last updated. Fri, 11 Jan 2013 3:50 pm CST
link Returns a url to the full forecast on Yahoo! Weather. View Forecast

One does not simply write docs

Note: You can use woeid.rosselliot.co.nz/lookup/ to find your locations unique WOEID.

simpleWeather is meant to be… well simple. You simply provide your US zip code, WOEID or any location in the world and it returns your local weather from Yahoo! This plugin won’t spit out a bunch of HTML full of classes and IDs. It just gives you the returned data for you to use, display and style as you need.

There are a few “gotcha” aspects for the Yahoo! API. If you are using a location instead of a zip code or WOEID the API is known to return multiple spots. For example a location of “Melbourne, Australia” will return the weather for Melbourne, Astralia and Melbourne Airport, Australia. When this happens the plugin returns the weather for the first location. If this is not giving you the desired result then you will need to either provide a US zip code or the WOEID.


Y u no ask questions?

1How do I change the language?

Currently the Yahoo! Weather API only returns en-us and does not provide a way for you to change this. If Yahoo! adds this feature then I will update simpleWeather to make use of it. If you have any other suggestions on providing translations feel free to let me know.

2My location does not return the correct weather?

If you are using the `location` param and having this issue it might be best to get your location’s WOEID following the steps above in the docs. Some locations only work with a very specific name. An example is London which does not work with a location of ‘london, uk’ instead only works as ‘london, united kingdom’.

3Can I use different weather icons instead of Yahoo’s?

As of v1.7 you have access to the condition code which can be used to use your own images. Now this will require having images for all (even if the same is used over) Condition Codes of which there are about 50. Basically you will need to name the images based on the condition code. Below is a quick example:

Now if the current weather is snow then the code returned is 16 in which case the above code will look for a 16.png image or whatever the condition code returned is. Yahoo! provides a description of each code found in the link above. If your not up to making your own icons but still aren’t satisfied with Yahoo’s there are plenty of free weather icon sets around. Here is a list found at WebResources Depot and a search ondeviantArt returns lots of quality sets. I also came across this great set recently – artill weather icons.

4Is it possible to display the forecast for the week?

The Yahoo! Weather API currently only returns today and tomorrow’s weather along with providing a link to view the full forecast. At the moment I’m unaware of a way to get a week.

5Can I use simpleWeather with WordPress?

Of course, the plugin only requires jQuery to work. However Matt McBrien has adapted the code into a WordPress Plugin. It gives the user a nice interface in the WP Admin. You can download it in the WordPress Plugin RepoPlease note that because the WP Plugin is developed by a third-party, I have no control over the code and it may not be updated with the latest version of the code. This also means that I am unable to provide support for the WP Plugin.

6Why yet another weather widget/plugin?

This plugin came about because I wanted control over what was displayed. I’ve used other widgets and plugins and found that none fit my needs. The biggest issue was not having control over the code it was spitting out. This included some plugins giving me crazy HTML with a bunch of classes. Why not write your own HTML? simpleWeather gives you all the available data and you choose what to use and how it should be display. This includes using your own HTML and CSS. More then that this means you can use the plugin for more then just displaying current weather. An example would be to create a dynamic design that changes based on the weather such as a header or images. simpleWeather makes it… well simple.

7Can I display the weather for multiple locations?

Yes, you can use the plugin to display the weather for multiple locations by calling $.simpleWeather({…});as many times as you want. This allows you to retrieve the weather for multiple locations and display each different if you wish.

8How can I display the current temp in both F and C?

As of version 1.9 you are able to do this. If your unit is set to F then based on the demo `weather.temp` shows the current temp in F and you can now use `weather.tempAlt` to display the temp in C. Same goes if the unit is set to C, `temp` is the degrees in that unit and `tempAlt` is in F. This only works with the current temp and not high, low, etc. If you are wanting to display more with both then you can use the same calculations in your success function.

9Oh no, the plugin is broke!

If you have any issues with simpleWeather you can submit an issue on GitHub. Please provide detail on the issue and jsfiddle your code.

 

第四个有关jquery 的weather转发

http://www.jqueryrain.com/?lT2JGO_K

If you’re working on a travel, news or other locally-oriented site, adding a display of the current weather conditions in the local area is the perfect touch. In the past, this was a relatively difficult task, involving server-side integration with weather APIs and more. Today, however, jQuery and YQL (a free web service offered by Yahoo) can be used to easily add a customized weather display to your site. In this article I’ll guide you through the process from start to finish.

Adding Weather to Your Site with jQuery and YQL
I’ll show you two possible looks for the finished widget. The first uses Yahoo Weather’s icons, and is purely academic(unless you receive permission to use the icons from Yahoo):

Weather 1

The second look uses the public icons specified in the Yahoo Weather data feeds:

Weather 2

In both cases, hovering over the icon displays the text for the condition – e.g. Fair or Sunny or Scattered Showers.

TUTORIAL DETAILS

  • Technologies: HTML, CSS, JavaScript, jQuery, YQL
  • Difficulty: Intermediate
  • Estimated Completion Time: 30-45 minutes

Introduction – The Power of YQL

In years gone by, using webservice data in a client-side web application required a proxy on a server (due to the AJAX cross-domain loading restrictions imposed by browsers), and often translation of data into JSON format so it would work easily with JavaScript. Today, however, there’s a much simpler option thanks to Yahoo’s free YQL (Yahoo! Query Language) service. What exactly is YQL? The rather broad definition given on the YQL site is:

The Yahoo! Query Language is an expressive SQL-like language that lets you query, filter, and join data across Web services. With YQL, apps run faster with fewer lines of code and a smaller network footprint.

Let’s put legs on that: YQL acts like a giant free proxy with powerful built-in data amalgamation tools. It can be used to easily integrate data from across the entire web into your client-side JavaScript applications. In other words, it’s a way to make really cool stuff while saving tons of time and work. If you aren’t familiar with YQL, you definitely should explore the YQL site. I won’t be going into much technical detail about using YQL in this tutorial; instead, I’ll just show what’s needed for the specific tasks we have.

USING YQL TO GET WEATHER CONDITIONS DATA

Now let’s look at the case at hand – getting weather data. One of the best sources of free weather data is Yahoo Weather’s RSS feeds. However, this data can’t be loaded via standard AJAX because it would require cross-domain loading. In the old days, we would have had to start setting up a proxy on our server. Today, though, we can use some YQL magic. Because YQL has the weather data built-in, we don’t even have to build any URL-based queries. We can use a simple query like this to retrieve the current weather and forecast for Manhattan:

1
SELECT * FROM weather.forecast WHERE location='10001'

To see this in action, go here and use the Test button. Note that you can choose the output format – XML or JSON.

In this tutorial, though, we don’t need the forecast. Here’s the query we can use to get just the current weather:

1
SELECT item.condition FROM weather.forecast WHERE location='10001'

To see this in action, go here and use the Test button. Here’s an example of the output we receive:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
mycallback({
 "query": {
  "count": 1,
  "created": "2011-06-23T19:54:07Z",
  "lang": "en-US",
  "results": {
   "channel": {
    "item": {
     "condition": {
      "code": "26",
      "date": "Thu, 23 Jun 2011 3:09 pm EDT",
      "temp": "70",
      "text": "Cloudy"
     }
    }
   }
  }
 }
});

In the query.results.channel.item.condition object, we find several items. First, code specifies the icon associated with the current conditions. The date property indicates the last update time. Finally, temp and text describe the current temperature and conditions respectively.

If you want the temperature in metric units, you can use this query:

1
SELECT item.condition FROM weather.forecast WHERE location='10001' AND u='c'

All of this sample code is great, but you probably want data for a location other than Manhattan. If you want to retrieve a US-based location, all you need to do is replace 10001 in the location parameter with the ZIP code of the desired location. If you want an international location, it’s a little more tricky.

For these locations, you’ll need to determine a special location code that uses the format CCRR0000, where the CCrepresents the country code, the RR represents the region code (just XX for most countries), and the 0000 represents the station ID. For example, the location code for Paris, France is FRXX0076. The easiest way to find an international location code is by going to Weather.com, searching for the location, going to its local weather page and noting the URL. Suppose you searched for Madrid, Spain. The URL in your browser for the local weather page looks like this:http://www.weather.com/weather/today/SPXX0050.

Note the code at the end – SPXX0050. This is the location code we need. So, the condition query for Madrid’s weather in metric units would be:

1
SELECT item.condition FROM weather.forecast WHERE location='SPXX0050' AND u='c'

Now that you understand where the data comes from and the query needed to get it, we’re ready to start writing code.

Getting Started with Code

You’ll need an HTML file to follow along with the tutorial. You can place it anywhere on your computer, and no testing server is needed; all code will be client-side. To simplify the tutorial, we’ll use inline CSS and JavaScript, but you’re welcome to use external .js or .css files if desired.

Tip: Want to experiment without cluttering up your computer with lots of files? For this type of tutorial, it can be helpful to use jsBin or jsFiddle to follow along. These free online tools let you experiment with HTML, JavaScript and CSS without having to create any files on your computer. Best of all, you can save, version and share your experiments.

If you’re starting with a blank HTML file, here’s the code you should have to start:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
    "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
 
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
  <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
 
  <title>Weather Widget</title>
  <style type="text/css">
  /* CSS will go here */
  
  </style>
</head>
<body>
  <!-- Markup will go here -->
  <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js"></script>
  <script type="text/javascript">
  // JavaScript will go here
 
  </script>
</body>
</html>

Note the designated places for markup, CSS and JavaScript. Additionally, note that we have included jQuery 1.6.1 from Google’s CDN.

Adding the HTML Markup

To create the widget as shown above, we’re going to have a dedicated wrapper div with several span elements within – one for the location text, one for the icon, and one for the temperature. Add the following markup to the body of your page:

1
2
3
4
5
6
7
<div id="wxWrap">
    <span id="wxIntro">
        Currently in Manhattan, NY:
    </span>
    <span id="wxIcon2"></span>
    <span id="wxTemp"></span>
</div>

Obviously, the Currently in Manhattan, NY text is optional, and can be customized as desired. Note the icon holder span:

1
<span id="wxIcon2"></span>

As mentioned before, there are two possible looks for the widget based on which icon set you use. In order to make it easy to experiment with both looks, we’ll write the code so that you can switch between them by simply changing the id on the icon span from wxIcon2 to wxIcon. Using wxIcon2 will cause the freely-usable icons to be used; using wxIconwill cause the Yahoo Weather icons to be used (just for experimenting). Here’s what the line should look like if you’re experimenting:

1
<span id="wxIcon"></span>

Note that we’re not creating a place to display the condition text (e.g. Sunny or Thunderstorm). This is because the icon will be configured to display that text in a tooltip on hover. However, if you want to display that text separately so it’s always visible, you could create a separate span and configure the JavaScript later on to fill it.

Adding the CSS Styling

Now we’re ready to add some styling. There are several points worthy of note:

  • The #wxWrap div will use progressive-enhancement CSS3 techniques to display rounded corners and a background gradient in browsers that support these styles. Older browsers will render square corners and a solid gray background.
  • To simplify vertical positioning, we use the inline-block display mode for each of the inner spans.
  • For the experimental icon holder #wxIcon, we are using the technique called CSS sprites. This means that all of the various weather icons are combined into one larger image. When displaying one of these icons, we use CSS background properties to display only the relevant small portion of that larger image. This technique means that only one image has to be loaded (versus many tiny individual files), thereby speeding up the page.

Add the following CSS to the style tag in the head of the page:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
#wxWrap {
    width: 350px;
    background: #EEE; /* Old browsers */
    background: -moz-linear-gradient(top, rgba(240,240,240,1) 0%, rgba(224,224,224,1) 100%); /* FF3.6+ */
    background: -webkit-gradient(linear, left top, left bottom, color-stop(0%,rgba(240,240,240,1)), color-stop(100%,rgba(224,224,224,1))); /* Chrome,Safari4+ */
    background: -webkit-linear-gradient(top, rgba(240,240,240,1) 0%,rgba(224,224,224,1) 100%); /* Chrome10+,Safari5.1+ */
    background: -o-linear-gradient(top, rgba(240,240,240,1) 0%,rgba(224,224,224,1) 100%); /* Opera11.10+ */
    background: -ms-linear-gradient(top, rgba(240,240,240,1) 0%,rgba(224,224,224,1) 100%); /* IE10+ */
    filter: progid:DXImageTransform.Microsoft.gradient( startColorstr='#f0f0f0', endColorstr='#e0e0e0',GradientType=0 ); /* IE6-9 */
    background: linear-gradient(top, rgba(240,240,240,1) 0%,rgba(224,224,224,1) 100%); /* W3C */
    padding: 2px 13px 2px 11px;
    -webkit-border-radius: 4px;
    -moz-border-radius: 4px;
    border-radius: 4px;
}
#wxIntro {
    display: inline-block;
    font: 14px/20px Arial,Verdana,sans-serif;
    color: #666;
    vertical-align: top;
    padding-top: 9px;
}
#wxIcon {
    display: inline-block;
    width: 61px;
    height: 34px;
    margin: 2px 0 -1px 1px;
    overflow: hidden;
    background: url('http://l.yimg.com/a/lib/ywc/img/wicons.png') no-repeat 61px 0;
}
#wxIcon2 {
    display: inline-block;
    width: 34px;
    height: 34px;
    margin: 1px 6px 0 8px;
    overflow: hidden;
}
#wxTemp {
    display: inline-block;
    font: 20px/28px Arial,Verdana,sans-serif;
    color: #333;
    vertical-align: top;
    padding-top: 5px;
    margin-left: 0;
}

The large list of background styles in the #wxWrap declaration (used to create the background gradient) were generated with the help of a CSS3 gradient generator. Also, note in the #wxIcon declaration that we make the background sprite image hidden at first (by positioning it off the edge); it will be positioned appropriately, revealing the relevant icon, once data has been loaded.

Most of the other styles are simply cosmetic, and can be customized if desired. If you’re using the experimental icons, you can use almost any background color because the icons are in PNG format and have a transparent background*. If you’re using the standard icons, though, you’ll want to keep a light-colored background because they are in GIF format and have a white matte.

* We don’t worry about IE6’s lack of compatibility for the transparent PNGs, since those icons are only for experimenting and even Microsoft has recommended abandoning IE6. If IE6 compatibility is critical for your needs, you can add a workaround.

Making Things Work with JavaScript + jQuery

Now we need to start adding JavaScript to make the widget functional. For simplicity, I’ll show the entire chunk of needed JavaScript first, then break it down bit by bit.

Add the following chunk of JavaScript code where denoted within the script tag at the bottom of the page:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
$(function(){
    // Specify the ZIP/location code and units (f or c)
    var loc = '10001'; // or e.g. SPXX0050
    var u = 'f';
    var query = "SELECT item.condition FROM weather.forecast WHERE location='" + loc + "' AND u='" + u + "'";
    var cacheBuster = Math.floor((new Date().getTime()) / 1200 / 1000);
    var url = 'http://query.yahooapis.com/v1/public/yql?q=' + encodeURIComponent(query) + '&format=json&_nocache=' + cacheBuster;
    window['wxCallback'] = function(data) {
        var info = data.query.results.channel.item.condition;
        $('#wxIcon').css({
            backgroundPosition: '-' + (61 * info.code) + 'px 0'
        }).attr({
            title: info.text
        });
        $('#wxIcon2').append('<img src="http://l.yimg.com/a/i/us/we/52/' + info.code + '.gif" width="34" height="34" title="' + info.text + '" />');
        $('#wxTemp').html(info.temp + '&deg;' + (u.toUpperCase()));
    };
    $.ajax({
        url: url,
        dataType: 'jsonp',
        cache: true,
        jsonpCallback: 'wxCallback'
    });
    
});

If you preview your page now, you should see the working widget in all of its sunny (or rainy) glory. If you update the markup by replacing

1
<span id="wxIcon2"></span>

with the alternative

1
<span id="wxIcon"></span>

as described above, you should also be able to see the experimental icons. Now, I’ll go into detail on what all of the code is actually doing.

JavaScript Breakdown – Overview

In summary, here’s what the above chunk does:

  • Everything is wrapped in the jQuery document.ready handler, so it executes as soon as the page is ready for manipulation.
  • First, the location and units are specified. These are used to then build a YQL query.
  • We take the query text and create a request URL for executing it on the YQL server.
  • We define a callback function to handle the data once it loads. This function updates the icons, condition text and temperature text.
  • Finally, we actually load the data via the jQuery.ajax function. We use the special jsonp (JSON+callback) format, which is required to work around cross-domain restrictions.

JavaScript Breakdown – Details

First up, the location and units are specified: Specify the ZIP/location code and units (f or c) var loc = '10001'; or e.g.SPXX0050 var u = 'f';

Naturally, you’ll want to update the loc variable with whatever location you want to use. As mentioned earlier, this should be a ZIP code within the US, or an international location code for other countries. The u variable specifies units – either Farenheit (via the default f) or Celcius (via c).

Now we have everything needed to build the YQL query:

1
var query = "SELECT item.condition FROM weather.forecast WHERE location='" + loc + "' AND u='" + u + "'";

The next step is to create the YQL request URL to execute that query. Here’s the basic format of a public YQL request URL:

1
http://query.yahooapis.com/v1/public/yql?q=URL_ENCODED_QUERY_HERE&format=json

Note the place for the URL-encoded query. Additionally, note that we have format=json appended on the end. This tells the YQL server to return the response in JSON format, allowing for easy use with JavaScript. YQL can also return results in XML format for situations where that format is more useful.

HANDLING CACHING

There’s still one more important factor that must be considered in building our YQL request – caching. Normally when making AJAX requests via jQuery, a special URL parameter is automatically appended to the request, passing either a random value or the current time. This ensures that the browser always makes a “fresh” request to the server. In our case, though, this isn’t what we want. We only want a “fresh” request to be made every 20 minutes or so, since most stations only report data once an hour. We want the browser to request fresh information, but not unnecessarily-fresh information.

When you’re building your own proxy, you have to worry about a complex setup to enable caching of requests. In our case, you’d have to write a script that only retrieves the weather from some service once every e.g. 20 minutes, and otherwise returns the most recently cached data. Thanks to YQL, though, we don’t have to worry about all of that. One of YQL’s best features is that it will automatically cache requests that have identical URLs. Moreover, requests that take advantage of cached data don’t have any request limits, meaning that properly-implemented caching usage can essentially remove all usage limits, period.

In order to take advantage of these YQL features, we want to create a URL that only changes periodically. For this example, I’ve chosen 20 minutes. We take the current time (via new Date().getTime()), then divide it by 1000 (to move from milliseconds to seconds), then divide it by 1200 (to move from seconds to 20-minute increments). Finally, we round it. The end value, thus, only changes once every 20 minutes. We take that value and then append it on the end of the request URL via a made-up _nocache parameter. Later on, we’ll disable jQuery’s automatic cache-busting as well, by passing cache:true to the jQuery.ajax call. This ensures that a unique request will only be made once every 20 minutes.

1
2
var cacheBuster = Math.floor((new Date().getTime()) / 1200 / 1000);
var url = 'http://query.yahooapis.com/v1/public/yql?q=' + encodeURIComponent(query) + '&format=json&_nocache=' + cacheBuster;

DEFINING THE LOAD HANDLER

Next up, we create the callback that will be executed once the weather data has loaded. For most AJAX requests, we would just define an anonymous function inline with the AJAX request. However, the problem is that jQuery would actually do the following with such a configuration:

  • jQuery would create a randomly-named global function, e.g. jQuery_callback_12345789
  • This newly-created global function would call the real handler we passed
  • Our request URL would be automatically updated so that it specified the new global function as the callback, via ...&callback=jQuery_callback_123456789

Usually this is helpful. But in our case, it would mean that every request has a unique URL, because the callback parameter would always be random; and that would disable the automatic YQL caching. So, to avoid this, we have to manually create a global function then pass its name via the jsonpCallback parameter in the jQuery.ajax call.

Here’s the load handler code:

1
2
3
4
5
6
7
8
9
10
window['wxCallback'] = function(data) {
    var info = data.query.results.channel.item.condition;
    $('#wxIcon').css({
        backgroundPosition: '-' + (61 * info.code) + 'px 0'
    }).attr({
        title: info.text
    });
    $('#wxIcon2').append('<img src="http://l.yimg.com/a/i/us/we/52/' + info.code + '.gif" width="34" height="34" title="' + info.text + '" />');
    $('#wxTemp').html(info.temp + '&deg;' + (u.toUpperCase()));
};

First, we reference the actual conditions object via data.query.results.channel.item.condition. This value is determined from the example JSON response included at the start of the tutorial. Then, we update the “experimental” icon if it exists. We update the background position using the numeric info.code value, so that only the relevant icon shows out of the larger sprite image. Additionally, we use info.text to set the title property on the span so that hovering over the icon will show e.g. Sunny or Cloudy.

Likewise, the “standard” icon holder is updated as well, by appending the specified icon image. The title attribute is set on the photo, so hovering will display the condition text in a tooltip.

Finally, we use the info.temp property to update the temperature display. I also appended a degree sign and the unit(°F or °C), but that’s optional.

MAKING THE ACTUAL AJAX REQUEST

Now that we have the request URL and the handler ready, we can make the actual AJAX request:

1
2
3
4
5
6
$.ajax({
    url: url,
    dataType: 'jsonp',
    cache: true,
    jsonpCallback: 'wxCallback'
});

Because we’re loading JSON, we’d usually use $.getJSON instead of $.ajax. However, as mentioned above, we’re going to override some of the default jQuery AJAX behaviors, so we need to use the lower-level $.ajax method. All four parameters are important:

  • url obviously specifies the URL we want to load from. We use the special YQL request URL that was determined earlier.
  • dataType is set to jsonp, so jQuery knows we’re loading in the JSON+callback format.
  • cache is enabled, so that jQuery won’t add its own cache-busting code. As mentioned above, we’re relying on the special cache buster value we appended to the URL manually.
  • jsonpCallback is used to specify wxCallback, the name of the global load handler function we just created. Again, this ensures that jQuery doesn’t try to help by creating a random function name that breaks caching.

And that’s it! You have a fully-functional widget that displays the current weather conditions for any location in the world, all while leveraging the advantages of YQL’s built-in caching.

Summary

In this tutorial, you’ve learned how jQuery and YQL can be used together to build powerful client-side web applications that consume all types of data. In this tutorial we specifically explored weather data, but there are numerous other possibilities – explore the data tables listed in the YQL console for more inspiration. Additionally, you’ve learned the needed tricks to take advantage of YQL’s powerful built-in caching features.

Thanks to your new knowledge, your website visitors will be able to enjoy the latest weather data on your site. Best of all, it only took a few lines of code and is highly flexible. Possible modifications and enhancements include displaying the condition text (e.g. Sunny or Cloudy), or displaying the forecast in addition to the current conditions. Have fun with your new skills!

 

 

总结一下 不是很好做, 要用json得到yahoo或者google的数据 明天看一下这些插件里有没有可以直接用json调用的 然后看看如何调用到自己的网站。

争取明天将weather的前台做好

 

 

 

 

发表评论

电子邮件地址不会被公开。 必填项已用*标注