slide-em-up 0.1.8 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
data/README.md CHANGED
@@ -6,13 +6,114 @@ a style and it displays it in HTML5. With a browser in full-screen, you can
6
6
  make amazing presentations!
7
7
 
8
8
 
9
+ How to do your first presentation with Slide'em up?
10
+ ---------------------------------------------------
11
+
12
+ 1. Install slide-em-up: `gem install slide-em-up`
13
+ 2. Create a directory for your presentation: `mkdir foobar && cd foobar`
14
+ 3. Create a section for your slides: `mkdir main_section`
15
+ 4. Write some slides: `vim main_section/slides.md`
16
+
17
+ !SLIDE
18
+ # My First slide #
19
+ It's awesome
20
+
21
+ !SLIDE
22
+ # My second slide #
23
+ This rocks too!
24
+
25
+ 5. Write the `presentation.json` file with the metadata:
26
+
27
+ {
28
+ "title": "My first presentation",
29
+ "theme": "shower",
30
+ "sections": ["main_section"]
31
+ }
32
+
33
+ 6. Launch the tool: `slide-em-up`
34
+ 7. Open your browser on http://localhost:9000/
35
+ 8. Use the arrows keys to navigate between the slides
36
+
37
+
38
+ Markup for the slides
39
+ ---------------------
40
+
41
+ This slides are writen in [Markdown](http://daringfireball.net/projects/markdown/syntax)
42
+ and `!SLIDE` is the indicator for a new slide.
43
+
44
+ Example:
45
+
46
+ !SLIDE
47
+ # Title of the first slide #
48
+ ## A subtitle ##
49
+ And some text...
50
+
51
+ !SLIDE
52
+ # Another slide #
53
+
54
+ * a
55
+ * bullet
56
+ * list
57
+
58
+ !SLIDE
59
+ # Third slide #
60
+
61
+ 1. **bold**
62
+ 2. _italics_
63
+ 3. https://github.com/
64
+
65
+
66
+ Syntax Highlighting
67
+ -------------------
68
+
69
+ To highlight some code in your slides, you have to install
70
+ [pygments](http://pygments.org/). Then, surround your code with backticks
71
+ like this:
72
+
73
+ ```ruby
74
+ class Foobar
75
+ def baz
76
+ puts "Foobar says baz"
77
+ end
78
+ end
79
+ ```
80
+
81
+
82
+ Themes
83
+ ------
84
+
85
+ Several themes are available: shower, 3d_slideshow and html5rocks.
86
+ To choose the theme for your presentation, edit the `presentation.json`
87
+ file and change the `"theme"` element.
88
+
89
+
90
+ Remote Control
91
+ --------------
92
+
93
+ When your start slide-em-up in console, a message says something like:
94
+
95
+ > Your remote key is 652df
96
+
97
+ This remote key can be used to send actions to browsers that display the
98
+ presentation. For example, this command goes to the next line:
99
+
100
+ curl http://localhost:9000/remote/652df/next
101
+
102
+ The last part of the URL is the action and can be `next`, `prev`, `up` or
103
+ `down`.
104
+
105
+ It's also possible to force slide-em-up to use a specific remote key by
106
+ setting the `APIKEY` environment variable:
107
+
108
+ APIKEY=foobar slide-em-up
109
+
110
+
9
111
  TODO
10
112
  ----
11
113
 
12
- * Explain how to install and use it in README
13
114
  * Same command line stuff than showoff
14
- * Many more things
15
- * Add more themes
115
+ * Add a showoff theme for compatibility
116
+ * Many more themes and features
16
117
 
17
118
 
18
119
  Issues or Suggestions
@@ -33,6 +134,7 @@ Scott Chacon is the guy who made [ShowOff](https://github.com/schacon/showoff).
33
134
  Slide'em up is only a copy of ShowOff, where sinatra was replaced by Goliath.
34
135
 
35
136
  Themes were picked from the internet. Thanks to:
137
+
36
138
  - Hakim El Hattab for 3d_slideshow
37
139
  - Google for html5rocks
38
140
  - Vadim Makeev for shower
data/bin/slide-em-up CHANGED
@@ -5,7 +5,9 @@ require "goliath/runner"
5
5
 
6
6
 
7
7
  presentation = SlideEmUp::Presentation.new(Dir.pwd)
8
+ key = ENV['APIKEY'] || rand(1_000_000).to_s(16)
9
+ puts "Your remote key is #{key}"
8
10
 
9
11
  runner = Goliath::Runner.new(ARGV, nil)
10
- runner.app = SlideEmUp::SlidesAPI.new(presentation)
12
+ runner.app = SlideEmUp::Routes.run(presentation, :remote_key => key)
11
13
  runner.run
@@ -16,7 +16,7 @@ module SlideEmUp
16
16
 
17
17
  def initialize(dir)
18
18
  infos = extract_normal_infos(dir) || extract_infos_from_showoff(dir) || {}
19
- infos = { "title" => "No title", "theme" => "default" }.merge(infos)
19
+ infos = { "title" => "No title", "theme" => "shower" }.merge(infos)
20
20
  @meta = build_meta(infos["title"], dir)
21
21
  @theme = build_theme(infos["theme"])
22
22
  @common = build_theme("common")
@@ -0,0 +1,52 @@
1
+ require "goliath/api"
2
+
3
+ module SlideEmUp
4
+ class RemoteAPI < Goliath::API
5
+ def initialize(key)
6
+ # Secret token...
7
+ @key = key
8
+
9
+ # Share channel between connections
10
+ @chan = ::EM::Channel.new
11
+ end
12
+
13
+ def response(env)
14
+ path_info = Rack::Utils.unescape(env['PATH_INFO'])
15
+ slash, key, action = path_info.split('/', 3)
16
+
17
+ # Events are public
18
+ return stream_events(env) if 'events' == action
19
+
20
+ # Sending events is restricted
21
+ return forbidden unless key == @key
22
+
23
+ @chan.push(action)
24
+ [200, {
25
+ "Content-Type" => "text/plain; charset=utf-8",
26
+ "Content-Length" => Rack::Utils.bytesize(action).to_s
27
+ }, [action]]
28
+ end
29
+
30
+ def on_close(env)
31
+ return unless env['subscription']
32
+ env.logger.info "Stream connection closed."
33
+ @chan.unsubscribe(env['subscription'])
34
+ end
35
+
36
+ protected
37
+
38
+ def stream_events(env)
39
+ env['subscription'] = @chan.subscribe do |msg|
40
+ env.stream_send("data: #{msg}\n\n")
41
+ end
42
+ streaming_response(200, {"Content-Type" => "text/event-stream"})
43
+ end
44
+
45
+ def forbidden
46
+ [403, {
47
+ "Content-Type" => "text/plain",
48
+ "Content-Length" => "10"
49
+ }, ["Forbidden\n"]]
50
+ end
51
+ end
52
+ end
@@ -0,0 +1,20 @@
1
+ require "rack/builder"
2
+
3
+
4
+ module SlideEmUp
5
+ class Routes
6
+
7
+ def self.run(presentation, opts = {})
8
+ Rack::Builder.new do
9
+ map '/remote' do
10
+ run SlideEmUp::RemoteAPI.new(opts[:remote_key])
11
+ end
12
+
13
+ map '/' do
14
+ run SlideEmUp::SlidesAPI.new(presentation)
15
+ end
16
+ end
17
+ end
18
+
19
+ end
20
+ end
@@ -1,3 +1,3 @@
1
1
  module SlideEmUp
2
- VERSION = "0.1.8"
2
+ VERSION = "0.2.0"
3
3
  end
data/lib/slide-em-up.rb CHANGED
@@ -1,5 +1,7 @@
1
1
  module SlideEmUp
2
- autoload :Presentation, "slide-em-up/presentation"
3
- autoload :SlidesAPI, "slide-em-up/slides_api"
4
- autoload :VERSION, "slide-em-up/version"
2
+ autoload :Presentation, "slide-em-up/presentation"
3
+ autoload :SlidesAPI, "slide-em-up/slides_api"
4
+ autoload :RemoteAPI, "slide-em-up/remote_api"
5
+ autoload :Routes, "slide-em-up/routes"
6
+ autoload :VERSION, "slide-em-up/version"
5
7
  end
@@ -42,11 +42,38 @@ var Slideshow = (function(){
42
42
  document.addEventListener('keydown', onDocumentKeyDown, false);
43
43
  document.addEventListener('touchstart', onDocumentTouchStart, false);
44
44
  window.addEventListener('hashchange', onWindowHashChange, false);
45
+
46
+ startEventSourceHandler('/remote/sub/events');
45
47
 
46
48
  // Read the initial state of the URL (hash)
47
49
  readURL();
48
50
  }
49
-
51
+
52
+ function startEventSourceHandler (uri) {
53
+ if (window['EventSource'] == undefined) return ;
54
+
55
+ var source = new EventSource(uri);
56
+
57
+ source.onmessage = function(e) {
58
+ switch(e.data){
59
+ case 'next':
60
+ Slideshow.navigateRight();
61
+ break;
62
+ case 'prev':
63
+ Slideshow.navigateLeft();
64
+ break;
65
+ case 'up':
66
+ Slideshow.navigateUp();
67
+ break;
68
+ case 'down':
69
+ Slideshow.navigateDown();
70
+ break;
71
+ default:
72
+ console.log(e);
73
+ };
74
+ };
75
+ }
76
+
50
77
  /**
51
78
  * Handler for the document level 'keydown' event.
52
79
  *
@@ -304,6 +304,7 @@
304
304
  function(e) { if (e.state) { _t.go(e.state); } }, false);
305
305
  query('#left-init-key').addEventListener('click',
306
306
  function() { _t.next(); }, false);
307
+ this._startEventSource('/remote/sub/events');
307
308
  this._update();
308
309
  };
309
310
 
@@ -320,6 +321,26 @@
320
321
  });
321
322
  return slideCount + 1;
322
323
  },
324
+ _startEventSource: function(uri) {
325
+ if (window['EventSource'] == undefined) return ;
326
+
327
+ var source = new EventSource(uri);
328
+ var _t = this;
329
+ source.onmessage = function(e) {
330
+ switch(e.data){
331
+ case 'next':
332
+ _t.next(); break;
333
+ case 'prev':
334
+ _t.prev(); break;
335
+ case 'up':
336
+ _t.showNotes(); break;
337
+ case 'down':
338
+ _t.switch3D(); break;
339
+ default:
340
+ console.log(e);
341
+ };
342
+ };
343
+ },
323
344
  _update: function(dontPush) {
324
345
  // in order to delay the time where the counter shows the slide number we check if
325
346
  // the slides are already loaded (so we show the loading... instead)
@@ -81,6 +81,47 @@
81
81
  }
82
82
  }
83
83
 
84
+ function startEventSourceHandler (uri) {
85
+ if (window['EventSource'] == undefined) return ;
86
+
87
+ var source = new EventSource(uri);
88
+ var current_slide_number = getCurrentSlideNumber();
89
+
90
+ source.onmessage = function(e) {
91
+ switch(e.data){
92
+ case 'next':
93
+ current_slide_number++;
94
+ goToSlide(current_slide_number);
95
+ break;
96
+ case 'prev':
97
+ current_slide_number--;
98
+ goToSlide(current_slide_number);
99
+ break;
100
+ case 'up':
101
+ if (!isSlideListMode()) {
102
+ e.preventDefault();
103
+
104
+ history.pushState(null, null, url.pathname + getSlideHashByNumber(current_slide_number));
105
+ enterSlideListMode();
106
+ scrollToCurrentSlide();
107
+ }
108
+ break;
109
+ case 'down':
110
+ if (isSlideListMode()) {
111
+ e.preventDefault();
112
+
113
+ history.pushState(null, null, url.pathname + '?full' + getSlideHashByNumber(current_slide_number));
114
+ enterSingleSlideMode();
115
+
116
+ updateProgress(current_slide_number);
117
+ }
118
+ break;
119
+ default:
120
+ console.log(e);
121
+ };
122
+ };
123
+ }
124
+
84
125
  window.addEventListener('DOMContentLoaded', function () {
85
126
  if (!isSlideListMode()) {
86
127
  // "?full" is present without slide hash so we should display first
@@ -210,4 +251,5 @@
210
251
  }
211
252
  }, false);
212
253
 
254
+ startEventSourceHandler('/remote/sub/events');
213
255
  }());
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: slide-em-up
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.8
4
+ version: 0.2.0
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,11 +9,11 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2011-08-28 00:00:00.000000000Z
12
+ date: 2011-09-13 00:00:00.000000000Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: goliath
16
- requirement: &75474350 !ruby/object:Gem::Requirement
16
+ requirement: &79848310 !ruby/object:Gem::Requirement
17
17
  none: false
18
18
  requirements:
19
19
  - - ~>
@@ -21,10 +21,10 @@ dependencies:
21
21
  version: '0.9'
22
22
  type: :runtime
23
23
  prerelease: false
24
- version_requirements: *75474350
24
+ version_requirements: *79848310
25
25
  - !ruby/object:Gem::Dependency
26
26
  name: redcarpet
27
- requirement: &75474100 !ruby/object:Gem::Requirement
27
+ requirement: &79852140 !ruby/object:Gem::Requirement
28
28
  none: false
29
29
  requirements:
30
30
  - - ~>
@@ -32,10 +32,10 @@ dependencies:
32
32
  version: '1.17'
33
33
  type: :runtime
34
34
  prerelease: false
35
- version_requirements: *75474100
35
+ version_requirements: *79852140
36
36
  - !ruby/object:Gem::Dependency
37
37
  name: erubis
38
- requirement: &75473870 !ruby/object:Gem::Requirement
38
+ requirement: &79874950 !ruby/object:Gem::Requirement
39
39
  none: false
40
40
  requirements:
41
41
  - - ~>
@@ -43,10 +43,10 @@ dependencies:
43
43
  version: '2.7'
44
44
  type: :runtime
45
45
  prerelease: false
46
- version_requirements: *75473870
46
+ version_requirements: *79874950
47
47
  - !ruby/object:Gem::Dependency
48
48
  name: yajl-ruby
49
- requirement: &75473640 !ruby/object:Gem::Requirement
49
+ requirement: &81723610 !ruby/object:Gem::Requirement
50
50
  none: false
51
51
  requirements:
52
52
  - - ~>
@@ -54,10 +54,10 @@ dependencies:
54
54
  version: '0.8'
55
55
  type: :runtime
56
56
  prerelease: false
57
- version_requirements: *75473640
57
+ version_requirements: *81723610
58
58
  - !ruby/object:Gem::Dependency
59
59
  name: albino
60
- requirement: &75473400 !ruby/object:Gem::Requirement
60
+ requirement: &82417980 !ruby/object:Gem::Requirement
61
61
  none: false
62
62
  requirements:
63
63
  - - ~>
@@ -65,10 +65,10 @@ dependencies:
65
65
  version: '1.3'
66
66
  type: :runtime
67
67
  prerelease: false
68
- version_requirements: *75473400
68
+ version_requirements: *82417980
69
69
  - !ruby/object:Gem::Dependency
70
70
  name: minitest
71
- requirement: &75473170 !ruby/object:Gem::Requirement
71
+ requirement: &83019290 !ruby/object:Gem::Requirement
72
72
  none: false
73
73
  requirements:
74
74
  - - ~>
@@ -76,7 +76,7 @@ dependencies:
76
76
  version: '2.3'
77
77
  type: :development
78
78
  prerelease: false
79
- version_requirements: *75473170
79
+ version_requirements: *83019290
80
80
  description: Slide'em up is a presentation tool that displays markdown-formatted slides
81
81
  email: bruno.michel@af83.com
82
82
  executables:
@@ -91,6 +91,8 @@ files:
91
91
  - bin/slide-em-up
92
92
  - lib/slide-em-up.rb
93
93
  - lib/slide-em-up/slides_api.rb
94
+ - lib/slide-em-up/remote_api.rb
95
+ - lib/slide-em-up/routes.rb
94
96
  - lib/slide-em-up/presentation.rb
95
97
  - lib/slide-em-up/version.rb
96
98
  - themes/shower/index.erb
@@ -143,7 +145,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
143
145
  version: '0'
144
146
  requirements: []
145
147
  rubyforge_project:
146
- rubygems_version: 1.8.5
148
+ rubygems_version: 1.8.10
147
149
  signing_key:
148
150
  specification_version: 3
149
151
  summary: Slide'em up is a presentation tool that displays markdown-formatted slides