/src/public/application.js

https://github.com/herestomwiththeweather/lascon-oauth · JavaScript · 124 lines · 82 code · 10 blank · 32 comment · 2 complexity · f60d6e8cf6af8eda223aff015c3b0b5d MD5 · raw file

  1. // Alias away the sync method
  2. Backbone._sync = Backbone.sync;
  3. // Override sync
  4. Backbone.sync = function(method, model, success, error) {
  5. // If we're making a twitter call ...
  6. if (model.url.indexOf('http://api.twitter.com') === 0) {
  7. // Do it with jsonp
  8. $.ajax({
  9. url: model.url,
  10. type: 'get',
  11. contentType: 'application/json',
  12. dataType: 'jsonp',
  13. success: success,
  14. error: error
  15. });
  16. } else {
  17. // otherwise make a normal call
  18. Backbone._sync(method, model, success, error);
  19. }
  20. };
  21. // Filter for which tweets to display. Defaults to all
  22. var TweetFilter = function(tweet) { return true; };
  23. // Empty model to hold our tweets
  24. var Tweet = Backbone.Model.extend({});
  25. // Tweet collection for fetching tweets
  26. var Tweets = Backbone.Collection.extend({
  27. model: Tweet,
  28. url: "http://api.twitter.com/1/statuses/public_timeline.json"
  29. });
  30. // Template for rendering tweets
  31. var TweetTemplate = _.template(
  32. "<div class='user span-4 '><%= model.get('user').screen_name %></div>"+
  33. "<div class='text span-20 last'><%= model.escape('text') %></div>"
  34. );
  35. // View for an individual tweet
  36. var TweetView = Backbone.View.extend({
  37. className: 'tweet span-24',
  38. initialize: function() {
  39. // This binds the render call so "this" is always this view
  40. _.bindAll(this, 'render');
  41. },
  42. render: function() {
  43. // Populate the template with our model
  44. $(this.el).html(TweetTemplate({model: this.model}));
  45. // for chaining
  46. return this;
  47. }
  48. });
  49. // View for the entire list of tweets
  50. var TweetList = new (Backbone.View.extend({
  51. // Bind to an existing element
  52. el: '#tweets',
  53. initialize: function() {
  54. _.bindAll(this, 'render');
  55. },
  56. render: function() {
  57. // empty the element
  58. $(this.el).html('');
  59. // select tweets that match the current filter and iterate
  60. _.each(Feed.select(TweetFilter), function(tweet) {
  61. // Append a tweetview to this element
  62. $(this.el).append(
  63. (new TweetView({model: tweet})).render().el
  64. );
  65. }, this);
  66. }
  67. }))();
  68. // View to handle find-as-you-type filtering
  69. var FilterView = new (Backbone.View.extend({
  70. // bind to existing element
  71. el: '#filter',
  72. // when keyup fires on the input, run the filter method
  73. events: {
  74. 'keyup input': 'filter'
  75. },
  76. initialize: function() {
  77. _.bindAll(this, 'filter', 'render');
  78. },
  79. render: function() {
  80. // Fill with static html
  81. $(this.el).html(
  82. "<div class='span-4'>Filter tweets by query</div>"+
  83. "<div class='span-20 last'>"+
  84. "<input type='text' />" +
  85. "</div>"
  86. );
  87. // And bind our events (this backbone method auto-clears events)
  88. this.delegateEvents(this.events);
  89. },
  90. filter: function() {
  91. // Set the global filter to return true for tweets
  92. // containing text that has the value of the filter field
  93. // in it somewhere
  94. TweetFilter = function(tweet) {
  95. return (tweet.escape('text').indexOf(this.$('input').val()) >= 0);
  96. };
  97. // When the filter changes, fire an event
  98. this.trigger('change:filter');
  99. }
  100. }))();
  101. // Setup the filter
  102. $(FilterView.render);
  103. // Instantiate a new feed
  104. var Feed = new Tweets();
  105. // When the feed is refreshed, render the list
  106. Feed.bind('refresh', TweetList.render);
  107. // When the filter changes, render the list
  108. FilterView.bind('change:filter', TweetList.render);
  109. // Auto-refresh the feed every 10 seconds
  110. var Refresh = function() {
  111. setTimeout(Refresh, 10000);
  112. Feed.fetch();
  113. };
  114. Refresh();