yellow-text-rails 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +17 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +48 -0
- data/Rakefile +1 -0
- data/lib/yellow-text-rails.rb +11 -0
- data/lib/yellow-text-rails/version.rb +5 -0
- data/vendor/assets/images/icon-s634930a1a1.png +0 -0
- data/vendor/assets/javascripts/yellow-text.js +467 -0
- data/vendor/assets/stylesheets/yellow-text.css +145 -0
- data/yellow-text-rails.gemspec +22 -0
- metadata +76 -0
data/.gitignore
ADDED
data/Gemfile
ADDED
data/LICENSE.txt
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
Copyright (c) 2013 Stefan Vermaas
|
2
|
+
|
3
|
+
MIT License
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
a copy of this software and associated documentation files (the
|
7
|
+
"Software"), to deal in the Software without restriction, including
|
8
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
the following conditions:
|
12
|
+
|
13
|
+
The above copyright notice and this permission notice shall be
|
14
|
+
included in all copies or substantial portions of the Software.
|
15
|
+
|
16
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
18
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,48 @@
|
|
1
|
+
![image](http://f.cl.ly/items/3A1s071l1H0M1c34210k/Schermafbeelding%202013-01-16%20om%2019.02.11.png)
|
2
|
+
|
3
|
+
# YellowText - Rails
|
4
|
+
|
5
|
+
Editing text shouldn't be a pain. It should be simple. It should be pretty. With Yellow Text it is.
|
6
|
+
|
7
|
+
This lightweight jQuery plugin can be used to make your text editing proces a lot easier and more fun. The text editor only contains the most basic functions you need for editing text.
|
8
|
+
|
9
|
+
For more information about the plugin, you should check [the official repo](https://github.com/stefanvermaas/yellow-text).
|
10
|
+
|
11
|
+
## Installation
|
12
|
+
|
13
|
+
Add this line to your application's Gemfile:
|
14
|
+
|
15
|
+
gem 'yellow-text-rails'
|
16
|
+
|
17
|
+
And then execute:
|
18
|
+
|
19
|
+
$ bundle
|
20
|
+
|
21
|
+
Or install it yourself as:
|
22
|
+
|
23
|
+
$ gem install yellow-text-rails
|
24
|
+
|
25
|
+
## Usage
|
26
|
+
|
27
|
+
**Step 1:**
|
28
|
+
Make sure you call the plugin by it's name
|
29
|
+
|
30
|
+
```javascript
|
31
|
+
$("#js-your-html-element").texteditor();
|
32
|
+
```
|
33
|
+
|
34
|
+
**Step 2:** Annnnnnnnnnd... finished! Wasn't that hard huh?!
|
35
|
+
|
36
|
+
## Beer-ware license
|
37
|
+
As long as you retain this notice you can do whatever you want with this stuff. If we meet some day, and you think this stuff is worth it, you can buy me a beer in return.
|
38
|
+
|
39
|
+
## Changelog
|
40
|
+
- v0.0.1: Very raw first version of the plugin
|
41
|
+
|
42
|
+
## Contributing
|
43
|
+
|
44
|
+
1. Fork it
|
45
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
46
|
+
3. Commit your changes (`git commit -am 'Add some feature'`)
|
47
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
48
|
+
5. Create new Pull Request
|
data/Rakefile
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
require "bundler/gem_tasks"
|
Binary file
|
@@ -0,0 +1,467 @@
|
|
1
|
+
/*!*
|
2
|
+
* Yellow Text
|
3
|
+
* =========================================
|
4
|
+
* This plugin is created to make text editing
|
5
|
+
* more fun and to make it easy for the editor.
|
6
|
+
*
|
7
|
+
* Version: 0.3
|
8
|
+
* Author: Stefan Vermaas
|
9
|
+
* URL: www.stefanvermaas.nl
|
10
|
+
*
|
11
|
+
*/
|
12
|
+
(function( $ ) {
|
13
|
+
|
14
|
+
// Define the plugin methods
|
15
|
+
var methods = {
|
16
|
+
|
17
|
+
// Call the initialization function
|
18
|
+
init: function( that, options ) {
|
19
|
+
|
20
|
+
// Create the global this element
|
21
|
+
methods.el = that;
|
22
|
+
|
23
|
+
/**
|
24
|
+
*
|
25
|
+
* Settings
|
26
|
+
* =========================================
|
27
|
+
* This part of the plugin contains the settings
|
28
|
+
* that are default. Feel free to override them
|
29
|
+
* during intialization of the plugin.
|
30
|
+
*
|
31
|
+
* For an example, see javascripts/demo.js
|
32
|
+
*
|
33
|
+
*/
|
34
|
+
methods.settings = $.extend( {
|
35
|
+
width : "100%",
|
36
|
+
height : "300px",
|
37
|
+
containerClass : "js-editor-container",
|
38
|
+
buttonsClass : "js-editor-buttons",
|
39
|
+
iFrameClass : "js-editor-iframe",
|
40
|
+
cleanOnSubmit : true,
|
41
|
+
defaultFont : "Helvetica Neue, Helvetica, arial, sans-serief",
|
42
|
+
defaultFontSize : "1em",
|
43
|
+
defaultFontColor : "#000000",
|
44
|
+
defaultActions : "bold, underline, italic, strikethrough, align-left, align-center, align-right, unorderd-list, ordered-list, link, image",
|
45
|
+
|
46
|
+
// Callbacks
|
47
|
+
isContentChanged : function() {},
|
48
|
+
setImage : function() {}
|
49
|
+
}, options);
|
50
|
+
|
51
|
+
// Render the plugin
|
52
|
+
methods.render();
|
53
|
+
|
54
|
+
// Grap the content and put it in the iframe
|
55
|
+
methods.setContent();
|
56
|
+
|
57
|
+
// Listen to events and react on them
|
58
|
+
methods.events();
|
59
|
+
},
|
60
|
+
|
61
|
+
/**
|
62
|
+
*
|
63
|
+
* Render
|
64
|
+
* =========================================
|
65
|
+
* This function renders the whole plugin and
|
66
|
+
* it's only used to build the plugin.
|
67
|
+
*
|
68
|
+
*/
|
69
|
+
render: function() {
|
70
|
+
|
71
|
+
// Render the new text editor
|
72
|
+
methods.createTextEditor();
|
73
|
+
|
74
|
+
// Render the buttons
|
75
|
+
methods.createButtons();
|
76
|
+
},
|
77
|
+
|
78
|
+
/**
|
79
|
+
*
|
80
|
+
* createTextEditor
|
81
|
+
* =========================================
|
82
|
+
* This part of the plugin builds the main
|
83
|
+
* elements of the new text editor
|
84
|
+
*
|
85
|
+
*/
|
86
|
+
createTextEditor: function() {
|
87
|
+
|
88
|
+
// Hide the current text field
|
89
|
+
$(methods.el).hide();
|
90
|
+
|
91
|
+
// Create a container which will hold or text editor
|
92
|
+
methods.container = $("<div />").addClass( methods.settings.containerClass ).css({
|
93
|
+
"float" : "left",
|
94
|
+
"width" : methods.settings.width,
|
95
|
+
"border" : "1px solid #ccc"
|
96
|
+
});
|
97
|
+
|
98
|
+
// Add the container after the element where we bind this plugin too
|
99
|
+
$(methods.el).after( methods.container );
|
100
|
+
|
101
|
+
// Create the iFrame and append to the previously created container
|
102
|
+
methods.editor = $("<iframe />").addClass( methods.settings.iFrameClass ).css({
|
103
|
+
"float" : "left",
|
104
|
+
"width" : methods.settings.width,
|
105
|
+
"height" : methods.settings.height,
|
106
|
+
"border" : "0",
|
107
|
+
"overflow": "hidden"
|
108
|
+
}).appendTo( methods.container ).get(0);
|
109
|
+
|
110
|
+
// Make the editor work in all browsers
|
111
|
+
methods.editor.contentWindow.document.open();
|
112
|
+
methods.editor.contentWindow.document.close();
|
113
|
+
methods.editor.contentWindow.document.designMode="on";
|
114
|
+
|
115
|
+
// Set the standard fonts etc
|
116
|
+
$(methods.editor).contents().find("body").css({
|
117
|
+
"word-wrap" : "break-word",
|
118
|
+
"font-family" : methods.settings.defaultFont,
|
119
|
+
"font-size" : methods.settings.defaultFontSize,
|
120
|
+
"color" : methods.settings.defaultFontColor
|
121
|
+
});
|
122
|
+
|
123
|
+
// Add some css to the iFrame
|
124
|
+
var iFrameCSS = '<style type="text/css">body{padding: 2%;} p { margin: 0; }</style>';
|
125
|
+
$(methods.editor).contents().find("head").append(iFrameCSS);
|
126
|
+
|
127
|
+
// Build the button container
|
128
|
+
methods.buttons = $("<div />").addClass( methods.settings.buttonsClass ).css({
|
129
|
+
"float" : "left",
|
130
|
+
"width" : methods.settings.width
|
131
|
+
}).prependTo( methods.container );
|
132
|
+
},
|
133
|
+
|
134
|
+
/**
|
135
|
+
*
|
136
|
+
* Content
|
137
|
+
* =========================================
|
138
|
+
* Graps the content from the textarea and puts
|
139
|
+
* it in the text editor
|
140
|
+
*
|
141
|
+
*/
|
142
|
+
setContent: function() {
|
143
|
+
|
144
|
+
// Grap the content of the textarea
|
145
|
+
var content = $(methods.el).text();
|
146
|
+
|
147
|
+
// Put the content of the textarea into the editor
|
148
|
+
$( methods.editor ).contents().find("body").append(content);
|
149
|
+
},
|
150
|
+
|
151
|
+
/**
|
152
|
+
*
|
153
|
+
* createButtons
|
154
|
+
* =========================================
|
155
|
+
* This part of the plugin build all the buttons
|
156
|
+
* that are defined by the user or it takes the
|
157
|
+
* default buttons.
|
158
|
+
*
|
159
|
+
*/
|
160
|
+
createButtons: function() {
|
161
|
+
|
162
|
+
// Define the "to make buttons"
|
163
|
+
var defaultOptions = methods.settings.defaultActions.split(/, ?/);
|
164
|
+
|
165
|
+
// Loop through all the buttons
|
166
|
+
for( i = 0; i < defaultOptions.length; i++ ) {
|
167
|
+
|
168
|
+
// Create a variable to store the object in
|
169
|
+
var button;
|
170
|
+
|
171
|
+
// Get the right value
|
172
|
+
switch( defaultOptions[i] ) {
|
173
|
+
case "bold" :
|
174
|
+
button = { content : "b", command : "bold" };
|
175
|
+
break;
|
176
|
+
case "underline" :
|
177
|
+
button = { content : "u", command : "underline" };
|
178
|
+
break;
|
179
|
+
case "italic" :
|
180
|
+
button = { content : "i", command : "italic" };
|
181
|
+
break;
|
182
|
+
case "strikethrough" :
|
183
|
+
button = { content : "s", command : "strikethrough" };
|
184
|
+
break;
|
185
|
+
case "align-left" :
|
186
|
+
button = { content : "left", command : "JustifyLeft" };
|
187
|
+
break;
|
188
|
+
case "align-center" :
|
189
|
+
button = { content : "center", command : "JustifyCenter" };
|
190
|
+
break;
|
191
|
+
case "align-right" :
|
192
|
+
button = { content : "right", command : "JustifyRight" };
|
193
|
+
break;
|
194
|
+
case "unorderd-list" :
|
195
|
+
button = { content : "ul", command : "InsertUnorderedList" };
|
196
|
+
break;
|
197
|
+
case "ordered-list" :
|
198
|
+
button = { content : "ol", command : "InsertOrderedList" };
|
199
|
+
break;
|
200
|
+
case "image" :
|
201
|
+
button = { content : "img", command : "image" };
|
202
|
+
break;
|
203
|
+
case "link" :
|
204
|
+
button = { content : "link", command : "link" };
|
205
|
+
break;
|
206
|
+
default :
|
207
|
+
button = { content : "", command : "" };
|
208
|
+
}
|
209
|
+
|
210
|
+
// Build the buttons and add before the container
|
211
|
+
$("<a />")
|
212
|
+
.addClass( button.command )
|
213
|
+
.text( button.content )
|
214
|
+
.attr( "data-command", button.command )
|
215
|
+
.appendTo( methods.buttons );
|
216
|
+
}
|
217
|
+
},
|
218
|
+
|
219
|
+
/**
|
220
|
+
*
|
221
|
+
* Events
|
222
|
+
* =========================================
|
223
|
+
* Listen to specific events. The events that
|
224
|
+
* are justed in this plugin are click, keydown
|
225
|
+
* and submit event
|
226
|
+
*
|
227
|
+
* With the click event we can detect a click on
|
228
|
+
* a button to modify the text.
|
229
|
+
*
|
230
|
+
* With the keydown event we can detect or the
|
231
|
+
* user uses shortkeys for editing text.
|
232
|
+
*
|
233
|
+
*/
|
234
|
+
events: function() {
|
235
|
+
|
236
|
+
// Bind to the click event on the buttons
|
237
|
+
$("." + methods.settings.buttonsClass + " a").on("click", function(e) {
|
238
|
+
|
239
|
+
// React on the button event
|
240
|
+
methods.buttonClicked( e, this );
|
241
|
+
});
|
242
|
+
|
243
|
+
// Bind to the keydown event while typing
|
244
|
+
$( methods.editor ).contents().find("body").on("keydown", function(e) {
|
245
|
+
|
246
|
+
// Check for a specific keycode
|
247
|
+
if( e.ctrlKey || e.metaKey ) {
|
248
|
+
methods.shortkey( e, this );
|
249
|
+
}
|
250
|
+
});
|
251
|
+
|
252
|
+
// Bind the keyup event, to check for changes
|
253
|
+
$( methods.editor ).contents().find("body").on("keyup", function(e) {
|
254
|
+
|
255
|
+
// Check or the text is changed
|
256
|
+
var changed = ( $( methods.editor ).contents().find("body").html() !== $(methods.el).text() ) ? true : false;
|
257
|
+
|
258
|
+
// Call the callback
|
259
|
+
methods.settings.isContentChanged( changed );
|
260
|
+
});
|
261
|
+
|
262
|
+
// Bind to the submit event of the form
|
263
|
+
$( methods.el ).parents("form").on("submit", function(e) {
|
264
|
+
|
265
|
+
// First clean the code
|
266
|
+
methods.cleanTheCode();
|
267
|
+
|
268
|
+
// Put the content back in the textfield
|
269
|
+
methods.putContentBack();
|
270
|
+
});
|
271
|
+
|
272
|
+
},
|
273
|
+
|
274
|
+
/**
|
275
|
+
*
|
276
|
+
* buttonClicked
|
277
|
+
* =========================================
|
278
|
+
* This function reacts on the fact that a
|
279
|
+
* button is clicked. Based on the button an
|
280
|
+
* action will be triggered
|
281
|
+
*
|
282
|
+
*/
|
283
|
+
buttonClicked: function( e, that ) {
|
284
|
+
|
285
|
+
// Get the command
|
286
|
+
var command = $(that).attr("data-command");
|
287
|
+
|
288
|
+
// Focus on the contentWindow
|
289
|
+
methods.editor.contentWindow.focus();
|
290
|
+
|
291
|
+
// Take an other look at the command and look for the perfect action and execute it
|
292
|
+
methods.runCMD( command );
|
293
|
+
|
294
|
+
// And focus back again on the contentWindow
|
295
|
+
methods.editor.contentWindow.focus();
|
296
|
+
},
|
297
|
+
|
298
|
+
/**
|
299
|
+
*
|
300
|
+
* shortkey
|
301
|
+
* =========================================
|
302
|
+
* Wanna use a shortkey? This function takes
|
303
|
+
* care for that. You can quickly edit the text
|
304
|
+
* by using those shortkeys.
|
305
|
+
*
|
306
|
+
* Currently you can use cmd/ctrl + b, cmd/ctrl + i
|
307
|
+
* and cmd/ctrl + u to make your text bold, italic
|
308
|
+
* or underlined.
|
309
|
+
*
|
310
|
+
*/
|
311
|
+
shortkey: function( e ) {
|
312
|
+
|
313
|
+
// Define command
|
314
|
+
var command;
|
315
|
+
|
316
|
+
// Focus on the contentWindow
|
317
|
+
methods.editor.contentWindow.focus();
|
318
|
+
|
319
|
+
// Detect for simple actions their functions
|
320
|
+
if( e.which === 66 ) {
|
321
|
+
command = "bold";
|
322
|
+
} else if( e.which === 73 ) {
|
323
|
+
command = "italic";
|
324
|
+
} else if( e.which === 85 ) {
|
325
|
+
command = "underline";
|
326
|
+
} else {
|
327
|
+
command = "";
|
328
|
+
}
|
329
|
+
|
330
|
+
// Run the command
|
331
|
+
methods.runCMD( command );
|
332
|
+
|
333
|
+
// And focus back again on the contentWindow
|
334
|
+
methods.editor.contentWindow.focus();
|
335
|
+
},
|
336
|
+
|
337
|
+
/**
|
338
|
+
*
|
339
|
+
* runCMD
|
340
|
+
* =========================================
|
341
|
+
* This is the real deal. This part of the
|
342
|
+
* script handles the actual commands and it
|
343
|
+
* can be used by every other function as long
|
344
|
+
* as it provides a command to execute.
|
345
|
+
*
|
346
|
+
*/
|
347
|
+
runCMD: function( cmd ) {
|
348
|
+
|
349
|
+
// Check command for special actions and run it
|
350
|
+
if( cmd === "image" ) {
|
351
|
+
|
352
|
+
// Check for the insertImage function, this will always be true
|
353
|
+
if( typeof methods.settings.setImage === "function" ) {
|
354
|
+
var image = methods.settings.setImage.call();
|
355
|
+
}
|
356
|
+
|
357
|
+
// Check or a other plugin or CMS added an image to the plugin
|
358
|
+
var url = ( typeof image !== "undefined" && image.length > 0 ) ? image : prompt("URL (example: http://www.google.com): ");
|
359
|
+
|
360
|
+
// Insert the image in the text editor
|
361
|
+
return methods.editor.contentWindow.document.execCommand( "InsertImage", false, url);
|
362
|
+
|
363
|
+
} else if( cmd === "link" ) {
|
364
|
+
var link = prompt("URL (example: http://www.google.com): ");
|
365
|
+
return methods.editor.contentWindow.document.execCommand( "CreateLink", false, link);
|
366
|
+
} else {
|
367
|
+
return methods.editor.contentWindow.document.execCommand( cmd );
|
368
|
+
}
|
369
|
+
},
|
370
|
+
|
371
|
+
/**
|
372
|
+
*
|
373
|
+
* cleanTheCode
|
374
|
+
* =========================================
|
375
|
+
* Now we're cleaning up someone's shit. The
|
376
|
+
* browsers insert really nasty code ( not semantic )
|
377
|
+
* in our text editor, but that won't stop us!
|
378
|
+
*
|
379
|
+
* We're gonna fight back. This function cleans
|
380
|
+
* the code and makes it pretty. Just like we want too.
|
381
|
+
*
|
382
|
+
*/
|
383
|
+
cleanTheCode: function() {
|
384
|
+
|
385
|
+
// Define the body element
|
386
|
+
var body = $(methods.editor).contents().find("body");
|
387
|
+
|
388
|
+
// Loop through each div tag and change it to a p tag
|
389
|
+
body.find("div").each( function() {
|
390
|
+
// Get the class if avaiable
|
391
|
+
var hasStyle = ( $(this).attr("style") ) ? true : false;
|
392
|
+
|
393
|
+
// Check or a element is not wrapped
|
394
|
+
if( $(this).parent("p").not("p") ) {
|
395
|
+
|
396
|
+
// Change the div elements to normal p tags
|
397
|
+
if( hasStyle ) {
|
398
|
+
// Wrap the content into p tags with the style
|
399
|
+
$(this).wrap("<p style=\"" + $(this).attr('style') + "\"></p>");
|
400
|
+
} else {
|
401
|
+
// Wrap the content into p tags
|
402
|
+
$(this).wrap("<p></p>");
|
403
|
+
}
|
404
|
+
}
|
405
|
+
|
406
|
+
// Unwrap all the div tags
|
407
|
+
$(this).contents().unwrap();
|
408
|
+
});
|
409
|
+
|
410
|
+
// Unwrap all br tags and remove the ugly div tags
|
411
|
+
body.find("br").unwrap();
|
412
|
+
|
413
|
+
// Find the first line
|
414
|
+
var firstLine = body.contents()[0];
|
415
|
+
|
416
|
+
// Check or the first line has a p tag surrounding it
|
417
|
+
if( body.find(firstLine).not("p") ) {
|
418
|
+
// The first line does not have a p tag
|
419
|
+
body.find(firstLine).wrap("p");
|
420
|
+
}
|
421
|
+
},
|
422
|
+
|
423
|
+
/**
|
424
|
+
*
|
425
|
+
* putContentBack
|
426
|
+
* =========================================
|
427
|
+
* This function is triggered on the submit
|
428
|
+
* event and is needed to put the content of
|
429
|
+
* the texteditor back in the text field
|
430
|
+
* where the plugin is binded too.
|
431
|
+
*
|
432
|
+
*/
|
433
|
+
putContentBack: function() {
|
434
|
+
// Grap the content of the iframe
|
435
|
+
var postData = $(methods.editor).contents().find("body").html();
|
436
|
+
|
437
|
+
// Add the data to the textarea, where this plugin is attached too
|
438
|
+
methods.el.html(postData);
|
439
|
+
}
|
440
|
+
};
|
441
|
+
|
442
|
+
|
443
|
+
// Initialize the plugin
|
444
|
+
$.fn.texteditor = function( method ) {
|
445
|
+
|
446
|
+
// Make sure the text editor can bind to all the HTML elements
|
447
|
+
return this.each( function() {
|
448
|
+
|
449
|
+
// Check for methods
|
450
|
+
if ( methods[method] ) {
|
451
|
+
|
452
|
+
// Target a specific function
|
453
|
+
return methods[method].apply( this, Array.prototype.slice.call( arguments, 1 ) );
|
454
|
+
} else if ( typeof method === 'object' || ! method ) {
|
455
|
+
|
456
|
+
// No specific method is found, just initialize the plugin
|
457
|
+
return methods.init( this, method );
|
458
|
+
} else {
|
459
|
+
|
460
|
+
// Method doesn't excist for this plugin
|
461
|
+
$.error( 'Method ' + method + ' does not exist on jQuery.texteditor' );
|
462
|
+
}
|
463
|
+
});
|
464
|
+
|
465
|
+
};
|
466
|
+
|
467
|
+
})( jQuery );
|
@@ -0,0 +1,145 @@
|
|
1
|
+
/**
|
2
|
+
*
|
3
|
+
* Yellow Text
|
4
|
+
* ========================================
|
5
|
+
* This is a pre-made theme for the Yellow
|
6
|
+
* text editor and it's not needed to run
|
7
|
+
* the plugin.
|
8
|
+
*
|
9
|
+
*/
|
10
|
+
.js-editor-container {
|
11
|
+
margin-top: 0.5em;
|
12
|
+
border: 1px solid #c9c8c8 !important;
|
13
|
+
border-radius: 3px;
|
14
|
+
box-shadow: 0 0 5px rgba(0, 0, 0, 0.15);
|
15
|
+
}
|
16
|
+
|
17
|
+
/**
|
18
|
+
*
|
19
|
+
* Buttons
|
20
|
+
* ========================================
|
21
|
+
* This section styles the buttons and the
|
22
|
+
* button bar, that holds all the buttons.
|
23
|
+
*
|
24
|
+
*/
|
25
|
+
.js-editor-buttons {
|
26
|
+
border-bottom: 1px solid rgba(0, 0, 0, 0.25);
|
27
|
+
background-image: -webkit-gradient(linear, 50% 0%, 50% 100%, color-stop(0%, #e8e8e8), color-stop(100%, #d2d1d1));
|
28
|
+
background-image: -webkit-linear-gradient(#e8e8e8, #d2d1d1);
|
29
|
+
background-image: -moz-linear-gradient(#e8e8e8, #d2d1d1);
|
30
|
+
background-image: -o-linear-gradient(#e8e8e8, #d2d1d1);
|
31
|
+
background-image: linear-gradient(#e8e8e8, #d2d1d1);
|
32
|
+
box-shadow: 0 1px 3px rgba(0, 0, 0, 0.15);
|
33
|
+
}
|
34
|
+
|
35
|
+
.js-editor-buttons > a {
|
36
|
+
display: block;
|
37
|
+
float: left;
|
38
|
+
width: 16px;
|
39
|
+
height: 16px;
|
40
|
+
margin: 8px;
|
41
|
+
font: 16px Georgia;
|
42
|
+
text-align: center;
|
43
|
+
text-transform: uppercase;
|
44
|
+
text-shadow: 0 1px #fff;
|
45
|
+
cursor: pointer;
|
46
|
+
}
|
47
|
+
|
48
|
+
.bold {
|
49
|
+
font-weight: bold;
|
50
|
+
}
|
51
|
+
|
52
|
+
.underline {
|
53
|
+
text-decoration: underline;
|
54
|
+
}
|
55
|
+
|
56
|
+
.italic {
|
57
|
+
font-style: italic;
|
58
|
+
}
|
59
|
+
|
60
|
+
.strikethrough {
|
61
|
+
text-decoration: line-through;
|
62
|
+
}
|
63
|
+
|
64
|
+
.icon-sprite, .JustifyLeft, .JustifyCenter, .JustifyRight, .InsertUnorderedList, .InsertOrderedList, .image, .link {
|
65
|
+
background: url('../images/icon-s634930a1a1.png') no-repeat;
|
66
|
+
}
|
67
|
+
|
68
|
+
.JustifyLeft,
|
69
|
+
.JustifyCenter,
|
70
|
+
.JustifyRight,
|
71
|
+
.InsertUnorderedList,
|
72
|
+
.InsertOrderedList,
|
73
|
+
.image,
|
74
|
+
.link {
|
75
|
+
margin-top: 9px;
|
76
|
+
text-indent: -99999em;
|
77
|
+
}
|
78
|
+
|
79
|
+
.JustifyLeft {
|
80
|
+
background-position: 0 -276px;
|
81
|
+
}
|
82
|
+
|
83
|
+
.JustifyCenter {
|
84
|
+
background-position: 0 -184px;
|
85
|
+
}
|
86
|
+
|
87
|
+
.JustifyRight {
|
88
|
+
background-position: 0 -230px;
|
89
|
+
}
|
90
|
+
|
91
|
+
.InsertUnorderedList {
|
92
|
+
background-position: 0 -138px;
|
93
|
+
}
|
94
|
+
|
95
|
+
.InsertOrderedList {
|
96
|
+
background-position: 0 -46px;
|
97
|
+
}
|
98
|
+
|
99
|
+
.image {
|
100
|
+
background-position: 0 -92px;
|
101
|
+
}
|
102
|
+
|
103
|
+
.link {
|
104
|
+
background-position: 0 0;
|
105
|
+
}
|
106
|
+
|
107
|
+
.js-editor-buttons a:first-child {
|
108
|
+
margin-left: 35px;
|
109
|
+
}
|
110
|
+
|
111
|
+
.js-editor-buttons a:nth-child(4) {
|
112
|
+
margin-right: 35px;
|
113
|
+
}
|
114
|
+
|
115
|
+
.js-editor-buttons a:nth-child(7) {
|
116
|
+
margin-right: 35px;
|
117
|
+
}
|
118
|
+
|
119
|
+
.js-editor-buttons a:nth-child(9) {
|
120
|
+
margin-right: 35px;
|
121
|
+
}
|
122
|
+
|
123
|
+
.js-editor-iframe {
|
124
|
+
box-shadow: inset 0 0 5px rgba(0, 0, 0, 0.25);
|
125
|
+
}
|
126
|
+
|
127
|
+
input[type="submit"] {
|
128
|
+
float: right;
|
129
|
+
margin-top: 10px;
|
130
|
+
padding: 7px 10px;
|
131
|
+
cursor: pointer;
|
132
|
+
-webkit-box-shadow: 0 1px 2px rgba(0, 0, 0, 0.25);
|
133
|
+
-moz-box-shadow: 0 1px 2px rgba(0, 0, 0, 0.25);
|
134
|
+
box-shadow: 0 1px 2px rgba(0, 0, 0, 0.25);
|
135
|
+
background-image: -webkit-gradient(linear, 50% 0%, 50% 100%, color-stop(0%, #e8e8e8), color-stop(100%, #d2d1d1));
|
136
|
+
background-image: -webkit-linear-gradient(top, #e8e8e8, #d2d1d1);
|
137
|
+
background-image: -moz-linear-gradient(top, #e8e8e8, #d2d1d1);
|
138
|
+
background-image: -o-linear-gradient(top, #e8e8e8, #d2d1d1);
|
139
|
+
background-image: linear-gradient(top, #e8e8e8, #d2d1d1);
|
140
|
+
border: 1px solid #a6a6a6;
|
141
|
+
border-radius: 3px;
|
142
|
+
font-size: 0.875em;
|
143
|
+
color: #666 !important;
|
144
|
+
text-shadow: 1px 1px #fff;
|
145
|
+
}
|
@@ -0,0 +1,22 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'yellow-text-rails/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |gem|
|
7
|
+
# Gem information
|
8
|
+
gem.name = "yellow-text-rails"
|
9
|
+
gem.version = YellowText::Rails::VERSION
|
10
|
+
gem.authors = ["Stefan Vermaas"]
|
11
|
+
gem.email = ["stefan@yellowduckwebdesign.nl"]
|
12
|
+
gem.homepage = "http://www.stefanvermaas.nl/yellow-text/"
|
13
|
+
gem.summary = "Yellow Text makes text editing fun again with a beautyful interface and a few very clean options"
|
14
|
+
|
15
|
+
# Project name
|
16
|
+
gem.rubyforge_project = "yellow-text-rails"
|
17
|
+
|
18
|
+
gem.files = `git ls-files`.split($/)
|
19
|
+
gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
|
20
|
+
gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
|
21
|
+
gem.require_paths = ["lib"]
|
22
|
+
end
|
metadata
ADDED
@@ -0,0 +1,76 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: yellow-text-rails
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
hash: 29
|
5
|
+
prerelease:
|
6
|
+
segments:
|
7
|
+
- 0
|
8
|
+
- 0
|
9
|
+
- 1
|
10
|
+
version: 0.0.1
|
11
|
+
platform: ruby
|
12
|
+
authors:
|
13
|
+
- Stefan Vermaas
|
14
|
+
autorequire:
|
15
|
+
bindir: bin
|
16
|
+
cert_chain: []
|
17
|
+
|
18
|
+
date: 2013-02-02 00:00:00 Z
|
19
|
+
dependencies: []
|
20
|
+
|
21
|
+
description:
|
22
|
+
email:
|
23
|
+
- stefan@yellowduckwebdesign.nl
|
24
|
+
executables: []
|
25
|
+
|
26
|
+
extensions: []
|
27
|
+
|
28
|
+
extra_rdoc_files: []
|
29
|
+
|
30
|
+
files:
|
31
|
+
- .gitignore
|
32
|
+
- Gemfile
|
33
|
+
- LICENSE.txt
|
34
|
+
- README.md
|
35
|
+
- Rakefile
|
36
|
+
- lib/yellow-text-rails.rb
|
37
|
+
- lib/yellow-text-rails/version.rb
|
38
|
+
- vendor/assets/images/icon-s634930a1a1.png
|
39
|
+
- vendor/assets/javascripts/yellow-text.js
|
40
|
+
- vendor/assets/stylesheets/yellow-text.css
|
41
|
+
- yellow-text-rails.gemspec
|
42
|
+
homepage: http://www.stefanvermaas.nl/yellow-text/
|
43
|
+
licenses: []
|
44
|
+
|
45
|
+
post_install_message:
|
46
|
+
rdoc_options: []
|
47
|
+
|
48
|
+
require_paths:
|
49
|
+
- lib
|
50
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
51
|
+
none: false
|
52
|
+
requirements:
|
53
|
+
- - ">="
|
54
|
+
- !ruby/object:Gem::Version
|
55
|
+
hash: 3
|
56
|
+
segments:
|
57
|
+
- 0
|
58
|
+
version: "0"
|
59
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
60
|
+
none: false
|
61
|
+
requirements:
|
62
|
+
- - ">="
|
63
|
+
- !ruby/object:Gem::Version
|
64
|
+
hash: 3
|
65
|
+
segments:
|
66
|
+
- 0
|
67
|
+
version: "0"
|
68
|
+
requirements: []
|
69
|
+
|
70
|
+
rubyforge_project: yellow-text-rails
|
71
|
+
rubygems_version: 1.8.24
|
72
|
+
signing_key:
|
73
|
+
specification_version: 3
|
74
|
+
summary: Yellow Text makes text editing fun again with a beautyful interface and a few very clean options
|
75
|
+
test_files: []
|
76
|
+
|