showoff 0.9.7.1 → 0.9.8

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 756658ffcc3440e126ed64c256a82ed7f188d1e0
4
- data.tar.gz: 6558c0816fe2ee1c4bfe1b18bf228b70f708a87e
3
+ metadata.gz: e0cff52fdf5f38360a5e10678acb81713da42532
4
+ data.tar.gz: 3dd12a4a362f8b0de756df4de1a34727533ee89c
5
5
  SHA512:
6
- metadata.gz: 2fe546cdf496d75232a11593820ef1070c66f4089598aaf9c9679d2f593446e0b47df3e6b08815180d21edac570e4f9e517ce28bb27277d26d8520d757eab551
7
- data.tar.gz: f6d1c58f94860d0f31982f91f3a64687fd80709a93f982a0c32a925a1189ecdf0ca6cfb773acb16495191d061e21f84762df78a0171efeb3769e13135a0cd6da
6
+ metadata.gz: fe5086466395d08f3667f90a76729d16d0546e5e57144ddf9a3dbcf69a1715f4cf57c6c658801f8a47d6ec4bb2e6090e707c69720eb7d4387d8670981d23b74b
7
+ data.tar.gz: 45a82534917bbdf68e3f792a381bac569a699184aa4bb3efe3b3013eda3b2367c89e3ef54f8b634d2ddaece0bd6b88fef46f7a171f9827ae23ac4e580028900b
data/bin/showoff CHANGED
@@ -99,6 +99,9 @@ command :serve do |c|
99
99
  c.desc 'Show verbose messaging'
100
100
  c.switch :verbose
101
101
 
102
+ c.desc 'Enable code review'
103
+ c.switch :review
104
+
102
105
  c.desc 'Port on which to run'
103
106
  c.default_value "9090"
104
107
  c.flag [:p,:port]
@@ -138,6 +141,7 @@ To run it from presenter view, go to: [ #{url}/presenter ]
138
141
  :pres_file => options[:f],
139
142
  :pres_dir => args[0],
140
143
  :verbose => options[:verbose],
144
+ :review => options[:review],
141
145
  :bind => options[:h]
142
146
  end
143
147
  end
data/lib/showoff.rb CHANGED
@@ -14,13 +14,15 @@ require "#{here}/commandline_parser"
14
14
  begin
15
15
  require 'RMagick'
16
16
  rescue LoadError
17
- $stderr.puts 'WARN: image sizing disabled - install rmagick'
17
+ $stderr.puts 'NOTICE: * automatic image sizing unavailable; install RMagick for this functionality.'
18
18
  end
19
19
 
20
20
  begin
21
21
  require 'pdfkit'
22
22
  rescue LoadError
23
- $stderr.puts 'WARN: pdf generation disabled - install pdfkit'
23
+ $stderr.puts 'NOTICE: * internal pdf generation disabled; install PDFKit for this functionality'
24
+ $stderr.puts 'NOTICE: the PDFKit integration will likely be deprecated. Instead, you should'
25
+ $stderr.puts 'NOTICE: simply use your browser to print from the /print endpoint.'
24
26
  end
25
27
 
26
28
  require 'tilt'
@@ -43,6 +45,8 @@ class ShowOff < Sinatra::Application
43
45
  set :presenters, []
44
46
 
45
47
  set :verbose, false
48
+ set :review, false
49
+
46
50
  set :pres_dir, '.'
47
51
  set :pres_file, 'showoff.json'
48
52
  set :page_size, "Letter"
@@ -69,6 +73,8 @@ class ShowOff < Sinatra::Application
69
73
  @logger.formatter = proc { |severity,datetime,progname,msg| "#{progname} #{msg}\n" }
70
74
  @logger.level = settings.verbose ? Logger::DEBUG : Logger::WARN
71
75
 
76
+ @review = settings.review
77
+
72
78
  dir = File.expand_path(File.join(File.dirname(__FILE__), '..'))
73
79
  @logger.debug(dir)
74
80
 
@@ -590,13 +596,21 @@ class ShowOff < Sinatra::Application
590
596
  @asset_path = "./"
591
597
  end
592
598
 
599
+ # Display favicon in the window if configured
600
+ @favicon = settings.showoff_config['favicon']
601
+
593
602
  # Check to see if the presentation has enabled feedback
594
- @feedback = settings.showoff_config['feedback']
603
+ @feedback = settings.showoff_config['feedback'] unless params[:feedback] == 'false'
604
+
605
+ # Provide a button in the sidebar for interactive editing if configured
606
+ @edit = settings.showoff_config['edit'] if @review
607
+
595
608
  erb :index
596
609
  end
597
610
 
598
611
  def presenter
599
612
  @issues = settings.showoff_config['issues']
613
+ @edit = settings.showoff_config['edit'] if @review
600
614
  @@cookie ||= guid()
601
615
  response.set_cookie('presenter', @@cookie)
602
616
  erb :presenter
@@ -645,17 +659,20 @@ class ShowOff < Sinatra::Application
645
659
 
646
660
  def onepage(static=false)
647
661
  @slides = get_slides_html(:static=>static, :toc=>true)
662
+ @favicon = settings.showoff_config['favicon']
648
663
  #@languages = @slides.scan(/<pre class=".*(?!sh_sourceCode)(sh_[\w-]+).*"/).uniq.map{ |w| "/sh_lang/#{w[0]}.min.js"}
649
664
  erb :onepage
650
665
  end
651
666
 
652
667
  def print(static=false)
653
668
  @slides = get_slides_html(:static=>static, :toc=>true, :print=>true)
669
+ @favicon = settings.showoff_config['favicon']
654
670
  erb :onepage
655
671
  end
656
672
 
657
673
  def supplemental(content, static=false)
658
674
  @slides = get_slides_html(:static=>static, :supplemental=>content)
675
+ @favicon = settings.showoff_config['favicon']
659
676
  @wrapper_classes = ['supplemental']
660
677
  erb :onepage
661
678
  end
@@ -665,6 +682,7 @@ class ShowOff < Sinatra::Application
665
682
  shared = Dir.glob("#{settings.pres_dir}/_files/share/*").map { |path| File.basename(path) }
666
683
  # We use the icky -999 magic index because it has to be comparable for the view sort
667
684
  @downloads = { -999 => [ true, 'Shared Files', shared ] }
685
+ @favicon = settings.showoff_config['favicon']
668
686
  rescue Errno::ENOENT => e
669
687
  # don't fail if the directory doesn't exist
670
688
  @downloads = {}
@@ -964,8 +982,7 @@ class ShowOff < Sinatra::Application
964
982
  protected! if settings.showoff_config['protected'].include? what
965
983
  end
966
984
 
967
- # this hasn't been set to anything remotely interesting for a long time now
968
- @asset_path = nil
985
+ @asset_path = env['SCRIPT_NAME'] == '' ? nil : env['SCRIPT_NAME'].gsub(/^\/?/, '/').gsub(/\/?$/, '/')
969
986
 
970
987
  begin
971
988
  if (what != "favicon.ico")
@@ -1,3 +1,3 @@
1
1
  # No namespace here since ShowOff is a class and I'd have to inherit from
2
2
  # Sinatra::Application (which we don't want to load here)
3
- SHOWOFF_VERSION = '0.9.7.1'
3
+ SHOWOFF_VERSION = '0.9.8'
@@ -38,6 +38,7 @@
38
38
  border-top-left-radius: 3px;
39
39
  border-top-right-radius: 3px;
40
40
  z-index: 2147483647; /* max, see http://www.puidokas.com/max-z-index/ */
41
+ display: none;
41
42
  }
42
43
  #followMode {
43
44
  display: none;
@@ -134,7 +135,8 @@
134
135
  }
135
136
 
136
137
  /* nested lists get their bullets back */
137
- .content ul ul {
138
+ .content ul ul,
139
+ .content ol ul {
138
140
  list-style: disc;
139
141
  margin: 10px 10px;
140
142
  padding-left: 40px;
@@ -299,6 +301,17 @@ img#disconnected {
299
301
  text-align: center;
300
302
  }
301
303
 
304
+ #feedbackSidebar div.row.tools {
305
+ position: absolute;
306
+ bottom: 30px;
307
+ width: 100%;
308
+ text-align: center;
309
+ }
310
+
311
+ #feedbackSidebar div.row.tools button#editSlide {
312
+ width: 90%%;
313
+ margin: auto 5%;
314
+ }
302
315
 
303
316
  .fg-menu-container {
304
317
  z-index: 2147483647; /* max, see http://www.puidokas.com/max-z-index/ */
@@ -487,10 +500,6 @@ ul#downloads li {
487
500
  margin: 0.5em;
488
501
  }
489
502
 
490
- span#issueUrl {
491
- display: none;
492
- }
493
-
494
503
  /**********************
495
504
  *** stats page ***
496
505
  **********************/
@@ -1,11 +1,12 @@
1
1
  // presenter js
2
2
  var slaveWindow = null;
3
+ var nextWindow = null;
3
4
 
4
5
  var paceData = [];
5
6
 
6
7
  $(document).ready(function(){
7
8
  // set up the presenter modes
8
- mode = { track: false, follow: true, update: true, slave: false };
9
+ mode = { track: false, follow: true, update: true, slave: false, next: false};
9
10
 
10
11
  // attempt to open another window for the presentation if the mode defaults
11
12
  // to enabling this. It does not by default, so this is likely a no-op.
@@ -103,9 +104,14 @@ function popupLoader(elem, page, id, event)
103
104
  }
104
105
 
105
106
  function reportIssue() {
106
- var slide = $("span#slideFile").text();
107
- var issues = $("span#issueUrl").text();
108
- var link = issues + encodeURIComponent('Issue with slide: ' + slide);
107
+ var slide = $("span#slideFile").text();
108
+ var link = issueUrl + encodeURIComponent('Issue with slide: ' + slide);
109
+ window.open(link);
110
+ }
111
+
112
+ function editSlide() {
113
+ var slide = $("span#slideFile").text();
114
+ var link = editUrl + slide + ".md";
109
115
  window.open(link);
110
116
  }
111
117
 
@@ -152,6 +158,58 @@ function openSlave()
152
158
  }
153
159
  }
154
160
 
161
+ function nextSlideNum(url) {
162
+ // Some fudging because the first slide is slide[0] but numbered 1 in the URL
163
+ console.log(typeof(url));
164
+ var snum;
165
+ if (typeof(url) == 'undefined') { snum = currentSlideFromParams()+1; }
166
+ else { snum = currentSlideFromParams()+2; }
167
+ return snum;
168
+ }
169
+
170
+ function toggleNext() {
171
+ mode.next = !mode.next;
172
+ openNext();
173
+ }
174
+
175
+ function openNext()
176
+ {
177
+ if (mode.next) {
178
+ try {
179
+ if(nextWindow == null || typeof(nextWindow) == 'undefined' || nextWindow.closed){
180
+ nextWindow = window.open('/?track=false&feedback=false&next=true#' + nextSlideNum(true),'','width=300,height=200');
181
+ }
182
+ else if(nextWindow.location.hash != '#' + nextSlideNum(true)) {
183
+ // maybe we need to reset content?
184
+ nextWindow.location.href = '/?track=false&feedback=false&next=true#' + nextSlideNum(true);
185
+ }
186
+
187
+ // maintain the pointer back to the parent.
188
+ nextWindow.presenterView = window;
189
+ nextWindow.mode = { track: false, next: true, follow: true };
190
+
191
+ $('#nextWindow').addClass('enabled');
192
+ }
193
+ catch(e) {
194
+ console.log('Failed to open or connect next window. Popup blocker?');
195
+ }
196
+
197
+ // Set up a maintenance loop to keep the connection between windows. I wish there were a cleaner way to do this.
198
+ //if (typeof maintainNext == 'undefined') {
199
+ // maintainNext = setInterval(openNext, 1000);
200
+ //}
201
+ }
202
+ else {
203
+ try {
204
+ nextWindow && nextWindow.close();
205
+ $('#nextWindow').removeClass('enabled');
206
+ }
207
+ catch (e) {
208
+ console.log('Next window failed to close properly.');
209
+ }
210
+ }
211
+ }
212
+
155
213
  function askQuestion(question) {
156
214
  $("#questions ul").prepend($('<li/>').text(question));
157
215
  }
@@ -264,11 +322,12 @@ function register() {
264
322
 
265
323
  function presPrevStep()
266
324
  {
267
- prevStep();
268
- try { slaveWindow.prevStep(false) } catch (e) {};
269
- postSlide();
325
+ prevStep();
326
+ try { slaveWindow.prevStep(false) } catch (e) {};
327
+ try { nextWindow.gotoSlide(nextSlideNum()) } catch (e) {};
328
+ postSlide();
270
329
 
271
- update();
330
+ update();
272
331
  }
273
332
 
274
333
  function presNextStep()
@@ -278,8 +337,9 @@ function presNextStep()
278
337
  incrCurr = slaveWindow.incrCurr
279
338
  incrSteps = slaveWindow.incrSteps
280
339
  */
281
- nextStep();
340
+ nextStep();
282
341
  try { slaveWindow.nextStep(false) } catch (e) {};
342
+ try { nextWindow.gotoSlide(nextSlideNum()) } catch (e) {};
283
343
  postSlide();
284
344
 
285
345
  update();
@@ -0,0 +1,137 @@
1
+ if (! this.sh_languages) {
2
+ this.sh_languages = {};
3
+ }
4
+ sh_languages['docker'] = [
5
+ [
6
+ [
7
+ /\b[+-]?(?:(?:0x[A-Fa-f0-9]+)|(?:(?:[\d]*\.)?[\d]+(?:[eE][+-]?[\d]+)?))u?(?:(?:int(?:8|16|32|64))|L)?\b/g,
8
+ 'sh_number',
9
+ -1
10
+ ],
11
+ [
12
+ /"/g,
13
+ 'sh_string',
14
+ 1
15
+ ],
16
+ [
17
+ /'/g,
18
+ 'sh_string',
19
+ 2
20
+ ],
21
+ [
22
+ /</g,
23
+ 'sh_string',
24
+ 3
25
+ ],
26
+ [
27
+ /\/[^\n]*\/\s/g, // anchor to \s to avoid matching directory names.
28
+ 'sh_regexp',
29
+ -1
30
+ ],
31
+ [
32
+ /(%r)(\{(?:\\\}|#\{[A-Za-z0-9]+\}|[^}])*\})/g,
33
+ ['sh_symbol', 'sh_regexp'],
34
+ -1
35
+ ],
36
+ [
37
+ /\b[A-Za-z0-9]+(?=\s*[=|\+]>)/g,
38
+ 'sh_attribute',
39
+ -1
40
+ ],
41
+ [
42
+ /\b(?:FROM|MAINTAINER|ENV|ADD|RUN|WORKDIR|VOLUME|ONBUILD|CMD|ENTRYPOINT|EXPOSE|USER)\b/g,
43
+ 'sh_keyword',
44
+ -1
45
+ ],
46
+ [
47
+ /(?:^\=begin)/g,
48
+ 'sh_comment',
49
+ 4
50
+ ],
51
+ [
52
+ /[A-Za-z0-9]+(?:\?|!)/g,
53
+ 'sh_normal',
54
+ -1
55
+ ],
56
+ [
57
+ /~|!|%|\^|\*|\(|\)|-|\+|=|\[|\]|\\|:|;|,|\.|\/|\?|&|<|>|\|/g,
58
+ 'sh_symbol',
59
+ -1
60
+ ],
61
+ [
62
+ /(#)(\{)/g,
63
+ ['sh_symbol', 'sh_cbracket'],
64
+ -1
65
+ ],
66
+ [
67
+ /#/g,
68
+ 'sh_comment',
69
+ 1
70
+ ],
71
+ [
72
+ /\{|\}/g,
73
+ 'sh_cbracket',
74
+ -1
75
+ ]
76
+ ],
77
+ [
78
+ [
79
+ /$/g,
80
+ null,
81
+ -2
82
+ ],
83
+ [
84
+ /\\(?:\\|")/g,
85
+ null,
86
+ -1
87
+ ],
88
+ [
89
+ /"/g,
90
+ 'sh_string',
91
+ -2
92
+ ]
93
+ ],
94
+ [
95
+ [
96
+ /$/g,
97
+ null,
98
+ -2
99
+ ],
100
+ [
101
+ /\\(?:\\|')/g,
102
+ null,
103
+ -1
104
+ ],
105
+ [
106
+ /'/g,
107
+ 'sh_string',
108
+ -2
109
+ ]
110
+ ],
111
+ [
112
+ [
113
+ /$/g,
114
+ null,
115
+ -2
116
+ ],
117
+ [
118
+ />/g,
119
+ 'sh_string',
120
+ -2
121
+ ]
122
+ ],
123
+ [
124
+ [
125
+ /^(?:\=end)/g,
126
+ 'sh_comment',
127
+ 5
128
+ ]
129
+ ],
130
+ [
131
+ [
132
+ /$/g,
133
+ null,
134
+ -2
135
+ ]
136
+ ]
137
+ ];
@@ -0,0 +1 @@
1
+ if(!this.sh_languages){this.sh_languages={}}sh_languages.docker=[[[/\b[+-]?(?:(?:0x[A-Fa-f0-9]+)|(?:(?:[\d]*\.)?[\d]+(?:[eE][+-]?[\d]+)?))u?(?:(?:int(?:8|16|32|64))|L)?\b/g,"sh_number",-1],[/"/g,"sh_string",1],[/'/g,"sh_string",2],[/</g,"sh_string",3],[/\/[^\n]*\/\s/g,"sh_regexp",-1],[/(%r)(\{(?:\\\}|#\{[A-Za-z0-9]+\}|[^}])*\})/g,["sh_symbol","sh_regexp"],-1],[/\b[A-Za-z0-9]+(?=\s*[=|\+]>)/g,"sh_attribute",-1],[/\b(?:FROM|MAINTAINER|ENV|ADD|RUN|WORKDIR|VOLUME|ONBUILD|CMD|ENTRYPOINT|EXPOSE|USER)\b/g,"sh_keyword",-1],[/(?:^\=begin)/g,"sh_comment",4],[/[A-Za-z0-9]+(?:\?|!)/g,"sh_normal",-1],[/~|!|%|\^|\*|\(|\)|-|\+|=|\[|\]|\\|:|;|,|\.|\/|\?|&|<|>|\|/g,"sh_symbol",-1],[/(#)(\{)/g,["sh_symbol","sh_cbracket"],-1],[/#/g,"sh_comment",1],[/\{|\}/g,"sh_cbracket",-1]],[[/$/g,null,-2],[/\\(?:\\|")/g,null,-1],[/"/g,"sh_string",-2]],[[/$/g,null,-2],[/\\(?:\\|')/g,null,-1],[/'/g,"sh_string",-2]],[[/$/g,null,-2],[/>/g,"sh_string",-2]],[[/^(?:\=end)/g,"sh_comment",5]],[[/$/g,null,-2]]];
data/public/js/showoff.js CHANGED
@@ -60,6 +60,9 @@ function setupPreso(load_slides, prefix) {
60
60
  // give us the ability to disable tracking via url parameter
61
61
  if(query.track == 'false') mode.track = false;
62
62
 
63
+ // make sure that the next view doesn't bugger things on the first load
64
+ if(query.next == 'true') mode.next = true;
65
+
63
66
  // Make sure the slides always look right.
64
67
  // Better would be dynamic calculations, but this is enough for now.
65
68
  $(window).resize(function(){location.reload();});
@@ -83,6 +86,7 @@ function setupPreso(load_slides, prefix) {
83
86
  $("#sendFeedback").click(function() {
84
87
  sendFeedback($( "input:radio[name=rating]:checked" ).val(), $("textarea#feedback").val())
85
88
  });
89
+ $("#editSlide").click(function() { editSlide(); });
86
90
 
87
91
  $("textarea#question").val(questionPrompt);
88
92
  $("textarea#feedback").val(feedbackPrompt);
@@ -90,7 +94,9 @@ function setupPreso(load_slides, prefix) {
90
94
  $("textarea#feedback").focus(function() { clearIf($(this), feedbackPrompt) });
91
95
 
92
96
  // Open up our control socket
93
- connectControlChannel();
97
+ if(mode.track) {
98
+ connectControlChannel();
99
+ }
94
100
  /*
95
101
  ws = new WebSocket('ws://' + location.host + '/control');
96
102
  ws.onopen = function() { connected(); };
@@ -195,17 +201,33 @@ function checkSlideParameter() {
195
201
  }
196
202
  }
197
203
 
204
+ function currentSlideFromName(name) {
205
+ var count = 0;
206
+ slides.each(function(s, slide) {
207
+ if (name == $(slide).find(".content").attr("ref") ) {
208
+ found = count;
209
+ return false;
210
+ }
211
+ count++;
212
+ });
213
+ return count;
214
+ }
215
+
198
216
  function currentSlideFromParams() {
199
217
  var result;
200
218
  if (result = window.location.hash.match(/#([0-9]+)/)) {
201
219
  return result[result.length - 1] - 1;
202
220
  }
221
+ else {
222
+ var hash = window.location.hash
223
+ return currentSlideFromName(hash.substr(1, hash.length))
224
+ }
203
225
  }
204
226
 
205
227
  function setupSlideParamsCheck() {
206
228
  var check = function() {
207
229
  var currentSlide = currentSlideFromParams();
208
- if (slidenum != currentSlide) {
230
+ if (!isNaN(currentSlide) && slidenum != currentSlide) {
209
231
  slidenum = currentSlide;
210
232
  showSlide();
211
233
  }
@@ -283,7 +305,7 @@ function showSlide(back_step, updatepv) {
283
305
  $('#slideFilename').text(fileName);
284
306
 
285
307
  // Update presenter view, if we spawned one
286
- if (updatepv && 'presenterView' in window) {
308
+ if (updatepv && 'presenterView' in window && ! mode.next) {
287
309
  var pv = window.presenterView;
288
310
  pv.slidenum = slidenum;
289
311
  pv.incrCurr = incrCurr
@@ -448,6 +470,13 @@ function track() {
448
470
  }
449
471
  }
450
472
 
473
+ // Open a new tab with an online code editor, if so configured
474
+ function editSlide() {
475
+ var slide = $("span#slideFilename").text();
476
+ var link = editUrl + slide + ".md";
477
+ window.open(link);
478
+ }
479
+
451
480
  function follow(slide) {
452
481
  if (mode.follow) {
453
482
  console.log("New slide: " + slide);
data/views/header.erb CHANGED
@@ -5,6 +5,10 @@
5
5
 
6
6
  <link rel="stylesheet" href="<%= @asset_path %>/css/reset.css" type="text/css"/>
7
7
 
8
+ <% if @favicon %>
9
+ <link rel="icon" href="<%= @favicon %>"/>
10
+ <% end %>
11
+
8
12
  <link type="text/css" href="<%= @asset_path %>/css/fg.menu.css" media="screen" rel="stylesheet" />
9
13
  <link type="text/css" href="<%= @asset_path %>/css/theme/ui.all.css" media="screen" rel="stylesheet" />
10
14
  <link type="text/css" href="<%= @asset_path %>/css/sh_style.css" rel="stylesheet" />
@@ -44,7 +48,9 @@
44
48
  <% end %>
45
49
 
46
50
  <script type="text/javascript">
47
- $(function(){
51
+ $(function(){
48
52
  setupPreso(<%= @slides.nil? ? "true" : "false"%>, '<%= @asset_path %>');
49
- });
53
+ });
54
+
55
+ editUrl = "<%= @edit %>";
50
56
  </script>
@@ -3,6 +3,10 @@
3
3
 
4
4
  <meta name="viewport" content="width=device-width"/>
5
5
 
6
+ <% if @favicon %>
7
+ <link rel="icon" href="<%= @favicon %>"/>
8
+ <% end %>
9
+
6
10
  <link rel="stylesheet" href="<%= @asset_path %>/css/reset.css" type="text/css"/>
7
11
  <link rel="stylesheet" href="<%= @asset_path %>/css/showoff.css" type="text/css"/>
8
12
 
data/views/index.erb CHANGED
@@ -41,6 +41,11 @@
41
41
  <textarea id="feedback"></textarea>
42
42
  <button id="sendFeedback">Send Feedback</button>
43
43
  </div>
44
+ <% if @edit then %>
45
+ <div class="row tools">
46
+ <button id="editSlide">Edit Current Slide</button>
47
+ </div>
48
+ <% end %>
44
49
  <div id="disclaimer">All features are anonymous</div>
45
50
  </div>
46
51
  <div id="feedbackHandle"></div>
data/views/onepage.erb CHANGED
@@ -5,6 +5,10 @@
5
5
  <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
6
6
  <title><%= @title %></title>
7
7
 
8
+ <% if @favicon %>
9
+ <link rel="icon" href="<%= @favicon %>"/>
10
+ <% end %>
11
+
8
12
  <% if @inline %>
9
13
 
10
14
  <%= inline_css(['reset.css', 'showoff.css', 'theme/ui.all.css', 'sh_style.css', 'onepage.css'], 'public/css') %>
data/views/presenter.erb CHANGED
@@ -6,12 +6,14 @@
6
6
  <%= erb :header %>
7
7
  <link rel="stylesheet" href="<%= @asset_path %>/css/presenter.css" type="text/css"/>
8
8
  <script type="text/javascript" src="<%= @asset_path %>/js/presenter.js"></script>
9
+ <script type="text/javascript">
10
+ editUrl = "<%= @edit %>";
11
+ issueUrl = "<%= @issues %>";
12
+ </script>
9
13
  </head>
10
14
 
11
15
  <body>
12
16
 
13
- <span id="issueUrl"><%= @issues %></span>
14
-
15
17
  <div id="help">
16
18
  <table>
17
19
  <tr><td class="key">z, ?</td><td>toggle help (this)</td></tr>
@@ -33,12 +35,16 @@
33
35
  </div>
34
36
  <span id="links">
35
37
  <span class="desktop">
38
+ <% if @edit %>
39
+ <a id="edit" href="javascript:editSlide();" title="Edit current slide in new window.">Edit Slide</a>
40
+ <% end %>
36
41
  <% if @issues %>
37
42
  <a id="report" href="javascript:reportIssue();" title="Report an issue with the current slide.">Report Issue With Slide</a>
38
43
  <% end %>
39
44
  <a id="stats" href="/stats" target="_showoffchild">Viewing Statistics</a>
40
45
  <a id="downloads" href="/download" target="_showoffchild">Downloads</a>
41
- <a id="slaveWindow" href="javascript:toggleSlave();" title="Enable the slave window.">Enable Slave Window</a>
46
+ <a id="slaveWindow" href="javascript:toggleSlave();" title="Enable the slave window.">Slave Window</a>
47
+ <a id="nextWindow" href="javascript:toggleNext();" title="Enable the next window view.">Next Window</a>
42
48
  <a id="generatePDF" href="/pdf" title="Call out to wkhtmltopdf to generate a PDF.">Generate PDF</a>
43
49
  <a id="onePage" href="/onepage" title="Load the single page view. Useful for printing.">Single Page</a>
44
50
  </span>
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: showoff
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.9.7.1
4
+ version: 0.9.8
5
5
  platform: ruby
6
6
  authors:
7
7
  - Scott Chacon
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-02-20 00:00:00.000000000 Z
11
+ date: 2014-04-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: sinatra
@@ -239,6 +239,8 @@ files:
239
239
  - public/js/sh_lang/sh_cucumber.min.js
240
240
  - public/js/sh_lang/sh_desktop.min.js
241
241
  - public/js/sh_lang/sh_diff.min.js
242
+ - public/js/sh_lang/sh_docker.js
243
+ - public/js/sh_lang/sh_docker.min.js
242
244
  - public/js/sh_lang/sh_erlang.min.js
243
245
  - public/js/sh_lang/sh_flex.min.js
244
246
  - public/js/sh_lang/sh_gherkin.js
@@ -301,7 +303,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
301
303
  version: '0'
302
304
  requirements: []
303
305
  rubyforge_project:
304
- rubygems_version: 2.0.3
306
+ rubygems_version: 2.0.14
305
307
  signing_key:
306
308
  specification_version: 4
307
309
  summary: The best damn presentation software a developer could ever love.