simple_form_markdown_editor 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +2 -0
- data/Gemfile +4 -0
- data/Gemfile.lock +126 -0
- data/README.md +111 -0
- data/Rakefile +1 -0
- data/app/controllers/simple_form_markdown_editor/previews_controller.rb +21 -0
- data/config/routes.rb +7 -0
- data/lib/assets/javascripts/simple_form_markdown_editor/simple_form_markdown_editor_buttons.js.coffee +135 -0
- data/lib/assets/javascripts/simple_form_markdown_editor/simple_form_markdown_editor_help.js.coffee +100 -0
- data/lib/assets/javascripts/simple_form_markdown_editor/simple_form_markdown_editor_tabs.js.coffee +84 -0
- data/lib/assets/javascripts/simple_form_markdown_editor.js +3 -0
- data/lib/assets/stylesheets/simple_form_markdown_editor/simple_form_markdown_editor.css.scss +275 -0
- data/lib/assets/stylesheets/simple_form_markdown_editor.css +3 -0
- data/lib/config/locales/simple_form_markdown_editor.en.yml +96 -0
- data/lib/simple_form_markdown_editor/configuration.rb +26 -0
- data/lib/simple_form_markdown_editor/engine.rb +4 -0
- data/lib/simple_form_markdown_editor/renderer.rb +50 -0
- data/lib/simple_form_markdown_editor/simple_form_markdown_editor.rb +183 -0
- data/lib/simple_form_markdown_editor/version.rb +3 -0
- data/lib/simple_form_markdown_editor.rb +21 -0
- data/simple_form_markdown_editor.gemspec +30 -0
- data/test/dummy/.gitignore +13 -0
- data/test/dummy/Gemfile +25 -0
- data/test/dummy/Gemfile.lock +195 -0
- data/test/dummy/README.rdoc +28 -0
- data/test/dummy/Rakefile +6 -0
- data/test/dummy/app/assets/images/.keep +0 -0
- data/test/dummy/app/assets/javascripts/application.js +4 -0
- data/test/dummy/app/assets/javascripts/editor_tests.coffee +3 -0
- data/test/dummy/app/assets/stylesheets/application.css +5 -0
- data/test/dummy/app/assets/stylesheets/editor_tests.scss +32 -0
- data/test/dummy/app/controllers/application_controller.rb +5 -0
- data/test/dummy/app/controllers/concerns/.keep +0 -0
- data/test/dummy/app/controllers/editor_tests_controller.rb +5 -0
- data/test/dummy/app/helpers/application_helper.rb +2 -0
- data/test/dummy/app/helpers/editor_tests_helper.rb +2 -0
- data/test/dummy/app/mailers/.keep +0 -0
- data/test/dummy/app/models/.keep +0 -0
- data/test/dummy/app/models/concerns/.keep +0 -0
- data/test/dummy/app/models/editor_test.rb +4 -0
- data/test/dummy/app/views/editor_tests/new.html.slim +2 -0
- data/test/dummy/app/views/layouts/application.html.erb +14 -0
- data/test/dummy/bin/bundle +3 -0
- data/test/dummy/bin/rails +8 -0
- data/test/dummy/bin/rake +8 -0
- data/test/dummy/bin/setup +29 -0
- data/test/dummy/bin/spring +15 -0
- data/test/dummy/config/application.rb +31 -0
- data/test/dummy/config/boot.rb +3 -0
- data/test/dummy/config/environment.rb +5 -0
- data/test/dummy/config/environments/development.rb +38 -0
- data/test/dummy/config/environments/production.rb +76 -0
- data/test/dummy/config/environments/test.rb +42 -0
- data/test/dummy/config/initializers/assets.rb +11 -0
- data/test/dummy/config/initializers/backtrace_silencers.rb +7 -0
- data/test/dummy/config/initializers/cookies_serializer.rb +3 -0
- data/test/dummy/config/initializers/filter_parameter_logging.rb +4 -0
- data/test/dummy/config/initializers/inflections.rb +16 -0
- data/test/dummy/config/initializers/mime_types.rb +4 -0
- data/test/dummy/config/initializers/session_store.rb +3 -0
- data/test/dummy/config/initializers/simple_form_markdown_editor.rb +5 -0
- data/test/dummy/config/initializers/wrap_parameters.rb +9 -0
- data/test/dummy/config/locales/en.yml +23 -0
- data/test/dummy/config/routes.rb +5 -0
- data/test/dummy/config/secrets.yml +22 -0
- data/test/dummy/config.ru +4 -0
- data/test/dummy/db/seeds.rb +7 -0
- data/test/dummy/lib/assets/.keep +0 -0
- data/test/dummy/lib/tasks/.keep +0 -0
- data/test/dummy/log/.keep +0 -0
- data/test/dummy/public/404.html +67 -0
- data/test/dummy/public/422.html +67 -0
- data/test/dummy/public/500.html +66 -0
- data/test/dummy/public/favicon.ico +0 -0
- data/test/dummy/public/robots.txt +5 -0
- data/test/dummy/test/controllers/.keep +0 -0
- data/test/dummy/test/controllers/editor_tests_controller_test.rb +7 -0
- data/test/dummy/test/fixtures/.keep +0 -0
- data/test/dummy/test/fixtures/editor_tests.yml +7 -0
- data/test/dummy/test/helpers/.keep +0 -0
- data/test/dummy/test/integration/.keep +0 -0
- data/test/dummy/test/mailers/.keep +0 -0
- data/test/dummy/test/models/.keep +0 -0
- data/test/dummy/test/models/editor_test_test.rb +7 -0
- data/test/dummy/test/test_helper.rb +7 -0
- data/test/dummy/vendor/assets/javascripts/.keep +0 -0
- data/test/dummy/vendor/assets/stylesheets/.keep +0 -0
- metadata +297 -0
@@ -0,0 +1,275 @@
|
|
1
|
+
@mixin clearfix {
|
2
|
+
&:after {
|
3
|
+
content: "";
|
4
|
+
display: table;
|
5
|
+
clear: both;
|
6
|
+
}
|
7
|
+
}
|
8
|
+
|
9
|
+
@mixin reset-list {
|
10
|
+
margin: 0;
|
11
|
+
padding: 0;
|
12
|
+
list-style: none;
|
13
|
+
}
|
14
|
+
|
15
|
+
@mixin default-font {
|
16
|
+
font-family: helvetica, arial, sans-serif;
|
17
|
+
font-size: 14px;
|
18
|
+
line-height: 16px;
|
19
|
+
font-weight: normal;
|
20
|
+
font-style: normal;
|
21
|
+
letter-spacing: 0;
|
22
|
+
color: $black;
|
23
|
+
}
|
24
|
+
|
25
|
+
$grey-light: rgb(240, 240, 240);
|
26
|
+
$grey: rgb(220, 220, 220);
|
27
|
+
$grey-dark: rgb(180, 180, 180);
|
28
|
+
$white: rgb(255, 255, 255);
|
29
|
+
$black: rgb(10, 10, 10);
|
30
|
+
|
31
|
+
// ====================================================================
|
32
|
+
|
33
|
+
div.simple_form_markdown_editor {
|
34
|
+
|
35
|
+
label {
|
36
|
+
display: block;
|
37
|
+
margin-bottom: 7px;
|
38
|
+
}
|
39
|
+
|
40
|
+
// --------------------------------------------------------------------
|
41
|
+
|
42
|
+
&[data-show="preview"] {
|
43
|
+
|
44
|
+
div.buttons,
|
45
|
+
div.help,
|
46
|
+
div.editor {
|
47
|
+
display: none;
|
48
|
+
}
|
49
|
+
|
50
|
+
div.preview {
|
51
|
+
display: block;
|
52
|
+
}
|
53
|
+
}
|
54
|
+
|
55
|
+
div.preview {
|
56
|
+
display: none;
|
57
|
+
}
|
58
|
+
|
59
|
+
div.editor {
|
60
|
+
textarea {
|
61
|
+
@include default-font;
|
62
|
+
border: 1px solid $grey;
|
63
|
+
border-radius: 2px;
|
64
|
+
width: 100%;
|
65
|
+
min-height: 176px;
|
66
|
+
margin: 0;
|
67
|
+
box-sizing: border-box;
|
68
|
+
padding: 7px;
|
69
|
+
box-shadow: inset 0 1px 2px $grey-light;
|
70
|
+
resize: vertical;
|
71
|
+
}
|
72
|
+
}
|
73
|
+
|
74
|
+
// --------------------------------------------------------------------
|
75
|
+
|
76
|
+
div.header {
|
77
|
+
div.editor_tabs {
|
78
|
+
background-color: $grey-light;
|
79
|
+
border: 1px solid $grey;
|
80
|
+
border-radius: 2px 2px 0 0;
|
81
|
+
margin-bottom: 16px;
|
82
|
+
|
83
|
+
ul.tabs {
|
84
|
+
@include reset-list;
|
85
|
+
padding: 8px 8px 0 8px;
|
86
|
+
margin-bottom: -1px;
|
87
|
+
|
88
|
+
li.tab {
|
89
|
+
display: inline-block;
|
90
|
+
&.active {
|
91
|
+
span {
|
92
|
+
background-color: white;
|
93
|
+
border-color: $grey;
|
94
|
+
color: $black;
|
95
|
+
}
|
96
|
+
}
|
97
|
+
span {
|
98
|
+
@include default-font;
|
99
|
+
color: $grey-dark;
|
100
|
+
display: inline-block;
|
101
|
+
border-top: 1px solid transparent;
|
102
|
+
border-left: 1px solid transparent;
|
103
|
+
border-right: 1px solid transparent;
|
104
|
+
border-radius: 2px 2px 0 0;
|
105
|
+
padding: 8px 14px;
|
106
|
+
cursor: pointer;
|
107
|
+
}
|
108
|
+
}
|
109
|
+
}
|
110
|
+
}
|
111
|
+
|
112
|
+
|
113
|
+
div.buttons {
|
114
|
+
ul.button_groups {
|
115
|
+
@include clearfix;
|
116
|
+
@include reset-list;
|
117
|
+
margin-bottom: 16px;
|
118
|
+
|
119
|
+
li.button_group {
|
120
|
+
color: red;
|
121
|
+
float: left;
|
122
|
+
margin-right: 8px;
|
123
|
+
|
124
|
+
&[data-buttons*='help'] {
|
125
|
+
float: right;
|
126
|
+
margin: 0;
|
127
|
+
}
|
128
|
+
|
129
|
+
ul.buttons {
|
130
|
+
@include clearfix;
|
131
|
+
@include reset-list;
|
132
|
+
|
133
|
+
li.button {
|
134
|
+
float: left;
|
135
|
+
|
136
|
+
&:first-child {
|
137
|
+
button {
|
138
|
+
border-radius: 2px 0 0 2px;
|
139
|
+
}
|
140
|
+
}
|
141
|
+
|
142
|
+
&:last-child {
|
143
|
+
button {
|
144
|
+
border-radius: 0 2px 2px 0;
|
145
|
+
border-right: 1px solid $grey;
|
146
|
+
}
|
147
|
+
}
|
148
|
+
|
149
|
+
&:first-child:last-child {
|
150
|
+
button {
|
151
|
+
border-radius: 2px;
|
152
|
+
border-right: 1px solid $grey;
|
153
|
+
}
|
154
|
+
}
|
155
|
+
|
156
|
+
button {
|
157
|
+
@include default-font;
|
158
|
+
display: inline-block;
|
159
|
+
background-color: white;
|
160
|
+
margin: 0;
|
161
|
+
padding: 0;
|
162
|
+
|
163
|
+
border: 0;
|
164
|
+
border-left: 1px solid $grey;
|
165
|
+
border-top: 1px solid $grey;
|
166
|
+
border-bottom: 1px solid $grey-dark;
|
167
|
+
|
168
|
+
padding: 4px 6px;
|
169
|
+
cursor: pointer;
|
170
|
+
|
171
|
+
&:active,
|
172
|
+
&.active {
|
173
|
+
border-color: $grey;
|
174
|
+
border-top-color: $grey-dark;
|
175
|
+
background-color: $grey-light;
|
176
|
+
}
|
177
|
+
}
|
178
|
+
}
|
179
|
+
}
|
180
|
+
}
|
181
|
+
}
|
182
|
+
}
|
183
|
+
}
|
184
|
+
|
185
|
+
div.help {
|
186
|
+
@include clearfix;
|
187
|
+
@include default-font;
|
188
|
+
transition: height .2s ease-in-out;
|
189
|
+
overflow: hidden;
|
190
|
+
height: 0;
|
191
|
+
box-sizing: border-box;
|
192
|
+
|
193
|
+
&[data-visible="true"] {
|
194
|
+
height: 210px;
|
195
|
+
margin-bottom: 16px;
|
196
|
+
}
|
197
|
+
|
198
|
+
div.help_wrapper {
|
199
|
+
height: 210px;
|
200
|
+
border: 1px solid $grey;
|
201
|
+
box-sizing: border-box;
|
202
|
+
> ul {
|
203
|
+
@include reset-list;
|
204
|
+
float: left;
|
205
|
+
width: 200px;
|
206
|
+
height: 100%;
|
207
|
+
border-right: 1px solid;
|
208
|
+
background-color: $grey-light;
|
209
|
+
|
210
|
+
> li {
|
211
|
+
padding: 8px 16px;
|
212
|
+
border-bottom: 1px solid $grey;
|
213
|
+
color: $grey-dark;
|
214
|
+
cursor: pointer;
|
215
|
+
|
216
|
+
&:hover {
|
217
|
+
color: $black;
|
218
|
+
}
|
219
|
+
}
|
220
|
+
}
|
221
|
+
|
222
|
+
ul.sections {
|
223
|
+
border-right-color: $grey-dark;
|
224
|
+
overflow-y: auto;
|
225
|
+
li.section {
|
226
|
+
&.active {
|
227
|
+
color: $black;
|
228
|
+
border-bottom: 1px solid $grey-dark;
|
229
|
+
background-color: $white;
|
230
|
+
}
|
231
|
+
}
|
232
|
+
}
|
233
|
+
|
234
|
+
ul.sub_sections {
|
235
|
+
border-right-color: $grey;
|
236
|
+
display: none;
|
237
|
+
overflow-y: auto;
|
238
|
+
&.active {
|
239
|
+
display: block;
|
240
|
+
}
|
241
|
+
li.sub_section {
|
242
|
+
background-color: $white;
|
243
|
+
&.active {
|
244
|
+
color: $black;
|
245
|
+
}
|
246
|
+
}
|
247
|
+
}
|
248
|
+
|
249
|
+
div.help_text {
|
250
|
+
padding: 8px 16px;
|
251
|
+
height: 100%;
|
252
|
+
box-sizing: border-box;
|
253
|
+
overflow-y: auto;
|
254
|
+
display: none;
|
255
|
+
|
256
|
+
p {
|
257
|
+
margin-top: 0;
|
258
|
+
}
|
259
|
+
|
260
|
+
code {
|
261
|
+
padding: 2px 3px;
|
262
|
+
font-family: Consolas, 'Liberation Mono', Menlo, Courier, monospace;
|
263
|
+
font-size: 13px;
|
264
|
+
background-color: $grey-light;
|
265
|
+
border-radius: 2px;
|
266
|
+
white-space: nowrap
|
267
|
+
}
|
268
|
+
|
269
|
+
&.active {
|
270
|
+
display: block;
|
271
|
+
}
|
272
|
+
}
|
273
|
+
}
|
274
|
+
}
|
275
|
+
}
|
@@ -0,0 +1,96 @@
|
|
1
|
+
en:
|
2
|
+
simple_form_markdown_editor:
|
3
|
+
tabs:
|
4
|
+
edit: Edit
|
5
|
+
preview: Preview
|
6
|
+
buttons:
|
7
|
+
ol: ol
|
8
|
+
ul: ul
|
9
|
+
h1: h1
|
10
|
+
h2: h2
|
11
|
+
h3: h3
|
12
|
+
h4: h4
|
13
|
+
h5: h5
|
14
|
+
h6: h6
|
15
|
+
blockquote: quote
|
16
|
+
hr: hr
|
17
|
+
code: code
|
18
|
+
strong: bold
|
19
|
+
em: italic
|
20
|
+
a: link
|
21
|
+
img: image
|
22
|
+
help: help
|
23
|
+
help:
|
24
|
+
block_elements:
|
25
|
+
title: Block Elements
|
26
|
+
elements:
|
27
|
+
paragraphs:
|
28
|
+
title: Paragraphs & Breaks
|
29
|
+
text: |+
|
30
|
+
To create a paragraph, simply create a block of text that is not separated by one or more blank lines. Blocks of text separated by one or more blank lines will be parsed as paragraphs.
|
31
|
+
|
32
|
+
If you want to create a line break, end a line with two or more spaces, then hit Return/Enter.
|
33
|
+
headers:
|
34
|
+
title: Headers
|
35
|
+
text: |+
|
36
|
+
Simply prefix your header text with the number of # characters to specify heading depth. For example: `# Header 1`, `## Header 2` and `### Header 3` will be progressively smaller headers. You may end your headers with any number of hashes.
|
37
|
+
blockquotes:
|
38
|
+
title: Blockquotes
|
39
|
+
text: |+
|
40
|
+
Markdown creates blockquotes email-style by prefixing each line with the `>`. This looks best if you decide to hard-wrap text and prefix each line with a `>` character, but Markdown supports just putting `>` before your paragraph.
|
41
|
+
lists:
|
42
|
+
title: Lists
|
43
|
+
text: |+
|
44
|
+
Markdown supports both ordered and unordered lists. To create an ordered list, simply prefix each line with a number (any number will do — this is why the editor only uses one number.) To create an unordered list, you can prefix each line with `*`, `+` or `-`.
|
45
|
+
|
46
|
+
List items can contain multiple paragraphs, however each paragraph must be indented by at least 4 spaces or a tab.
|
47
|
+
code_blocks:
|
48
|
+
title: Code Blocks
|
49
|
+
text: |+
|
50
|
+
Markdown wraps code blocks in pre-formatted tags to preserve indentation in your code blocks. To create a code block, indent the entire block by at least 4 spaces or one tab. Markdown will strip the extra indentation you’ve added to the code block.
|
51
|
+
horizontal_rules:
|
52
|
+
title: Horizontal Rules
|
53
|
+
text: |+
|
54
|
+
Horizontal rules are created by placing three or more hyphens, asterisks or underscores on a line by themselves. Spaces are allowed between the hyphens, asterisks or underscores.
|
55
|
+
span_elements:
|
56
|
+
title: Span Elements
|
57
|
+
elements:
|
58
|
+
links:
|
59
|
+
title: Links
|
60
|
+
text: |+
|
61
|
+
Markdown has two types of links: inline and reference. For both types of links, the text you want to display to the user is placed in square brackets. For example, if you want your link to display the text “GitHub”, you write `[GitHub]`.
|
62
|
+
|
63
|
+
To create an inline link, create a set of parentheses immediately after the brackets and write your URL within the parentheses. (e.g., `[GitHub](https://github.com/)`). Relative paths are allowed in inline links.
|
64
|
+
|
65
|
+
To create a reference link, use two sets of square brackets. `[[my internal link|internal-ref]]` will link to the internal reference internal-ref.
|
66
|
+
emphasis:
|
67
|
+
title: Emphasis
|
68
|
+
text: |+
|
69
|
+
Asterisks (`*`) and underscores (`_`) are treated as emphasis and are wrapped with an `<em>` tag, which usually displays as italics in most browsers. Double asterisks (`**`) or double underscores (`__`) are treated as bold using the `<strong>` tag.
|
70
|
+
|
71
|
+
To create italic or bold text, simply wrap your words in single/double asterisks/underscores. For example, `**My double emphasis text**` becomes **My double emphasis text**, and `*My single emphasis text*` becomes *My single emphasis text*.
|
72
|
+
code:
|
73
|
+
title: Code
|
74
|
+
text: |+
|
75
|
+
To create inline spans of code, simply wrap the code in backticks (`` ` ``). Markdown will turn `` `myFunction` `` into `myFunction`.
|
76
|
+
images:
|
77
|
+
title: Images
|
78
|
+
text: |+
|
79
|
+
Markdown image syntax looks a lot like the syntax for links; it is essentially the same syntax preceded by an exclamation point (`!`).
|
80
|
+
|
81
|
+
For example, if you want to link to an image at https://github.com/unicorn.png with the alternate text My Unicorn, you would write `![My Unicorn](https://github.com/unicorn.png)`.
|
82
|
+
miscellaneous:
|
83
|
+
title: Miscellaneous
|
84
|
+
elements:
|
85
|
+
automatic_links:
|
86
|
+
title: Automatic Links
|
87
|
+
text: |+
|
88
|
+
If you want to create a link that displays the actual URL, markdown allows you to quickly wrap the URL in `<` and `>` to do so.
|
89
|
+
|
90
|
+
For example, the link https://github.com/ is easily produced by writing `<https://github.com/>`.
|
91
|
+
escaping:
|
92
|
+
title: Escaping
|
93
|
+
text: |+
|
94
|
+
If you want to use a special Markdown character in your document (such as displaying literal asterisks), you can escape the character with the backslash (`\`). Markdown will ignore the character directly after a backslash.
|
95
|
+
loading: Loading preview …
|
96
|
+
nothing_to_preview: Nothing to preview.
|
@@ -0,0 +1,26 @@
|
|
1
|
+
module SimpleFormMarkdownEditor
|
2
|
+
class Configuration
|
3
|
+
|
4
|
+
attr_accessor :buttons
|
5
|
+
attr_accessor :extensions
|
6
|
+
attr_accessor :help
|
7
|
+
attr_accessor :render_options
|
8
|
+
|
9
|
+
def initialize
|
10
|
+
@buttons = [%w(h1 h2 h3), %w(a img), %w(strong em code), %w(ul ol blockquote hr), %w(help)]
|
11
|
+
@help = {
|
12
|
+
enabled: true,
|
13
|
+
visible: false
|
14
|
+
}
|
15
|
+
@extensions = {
|
16
|
+
footnotes: true,
|
17
|
+
highlight: true,
|
18
|
+
space_after_headers: true,
|
19
|
+
strikethrough: true,
|
20
|
+
superscript: true
|
21
|
+
}
|
22
|
+
@render_options = {}
|
23
|
+
end
|
24
|
+
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
require 'redcarpet'
|
2
|
+
|
3
|
+
module SimpleFormMarkdownEditor
|
4
|
+
class Renderer
|
5
|
+
|
6
|
+
def self.call(*args)
|
7
|
+
new(*args).call
|
8
|
+
end
|
9
|
+
|
10
|
+
# =====================================================================
|
11
|
+
|
12
|
+
attr_reader :str
|
13
|
+
|
14
|
+
def initialize str
|
15
|
+
@str = str
|
16
|
+
end
|
17
|
+
|
18
|
+
def call
|
19
|
+
markdown_renderer.render(@str).html_safe
|
20
|
+
end
|
21
|
+
|
22
|
+
private # =============================================================
|
23
|
+
|
24
|
+
def markdown_renderer
|
25
|
+
Redcarpet::Markdown.new(
|
26
|
+
Redcarpet::Render::HTML.new(self.class.configuration.render_options),
|
27
|
+
self.class.configuration.extensions
|
28
|
+
)
|
29
|
+
end
|
30
|
+
|
31
|
+
# ---------------------------------------------------------------------
|
32
|
+
|
33
|
+
class << self
|
34
|
+
attr_accessor :configuration
|
35
|
+
|
36
|
+
def configure
|
37
|
+
@configuration ||= Configuration.new
|
38
|
+
yield @configuration
|
39
|
+
end
|
40
|
+
|
41
|
+
def configuration
|
42
|
+
@configuration ||= Configuration.new
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
end
|
47
|
+
|
48
|
+
# ---------------------------------------------------------------------
|
49
|
+
|
50
|
+
end
|
@@ -0,0 +1,183 @@
|
|
1
|
+
require 'simple_form'
|
2
|
+
require 'i18n'
|
3
|
+
|
4
|
+
module SimpleFormMarkdownEditor
|
5
|
+
class MarkdownEditorInput < SimpleForm::Inputs::Base
|
6
|
+
|
7
|
+
class << self
|
8
|
+
attr_accessor :configuration
|
9
|
+
|
10
|
+
def configure
|
11
|
+
@configuration ||= Configuration.new
|
12
|
+
yield @configuration
|
13
|
+
end
|
14
|
+
|
15
|
+
def configuration
|
16
|
+
@configuration ||= Configuration.new
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
# =====================================================================
|
21
|
+
|
22
|
+
def input wrapper_options
|
23
|
+
template.content_tag :div, merge_wrapper_options(input_html_options, wrapper_options) do
|
24
|
+
header + help + editor + preview
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
private # =============================================================
|
29
|
+
|
30
|
+
def input_html_options
|
31
|
+
super.merge!(data: { preview_url: SimpleFormMarkdownEditor::Engine.routes.url_helpers.preview_path })
|
32
|
+
end
|
33
|
+
|
34
|
+
def input_html_classes
|
35
|
+
super.push('simple_form_markdown_editor')
|
36
|
+
end
|
37
|
+
|
38
|
+
def header
|
39
|
+
template.content_tag :div, class: 'header' do
|
40
|
+
tabs + buttons
|
41
|
+
end.html_safe
|
42
|
+
end
|
43
|
+
|
44
|
+
# ---------------------------------------------------------------------
|
45
|
+
|
46
|
+
def tabs
|
47
|
+
template.content_tag :div, class: 'editor_tabs' do
|
48
|
+
template.content_tag :ul, class: 'tabs' do
|
49
|
+
tab_list.map{ |t| tab(t) }.flatten.join.html_safe
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
def tab_list
|
55
|
+
%w(edit preview)
|
56
|
+
end
|
57
|
+
|
58
|
+
def tab name
|
59
|
+
template.content_tag :li, class: ['tab', name.to_s.underscore.downcase], data: { command: name.to_s } do
|
60
|
+
template.content_tag :span, I18n.t(name.to_sym, scope: 'simple_form_markdown_editor.tabs'), class: name.to_s.underscore.downcase
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
# ---------------------------------------------------------------------
|
65
|
+
|
66
|
+
def buttons
|
67
|
+
template.content_tag :div, class: 'buttons' do
|
68
|
+
button_groups
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
def button_groups
|
73
|
+
template.content_tag :ul, class: 'button_groups' do
|
74
|
+
button_list.map{ |group| button_group(group) }.flatten.join.html_safe
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
def button_group g
|
79
|
+
template.content_tag :li, class: 'button_group', data: { buttons: g.join(' ') } do
|
80
|
+
template.content_tag :ul, class: 'buttons' do
|
81
|
+
g.map{ |b| button(b) }.flatten.join.html_safe
|
82
|
+
end
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
def button b
|
87
|
+
return if b == 'help' && !help_enabled?
|
88
|
+
template.content_tag :li, class: ['button', b], data: { toggle: b } do
|
89
|
+
template.content_tag :button, I18n.t(b.to_sym, scope: 'simple_form_markdown_editor.buttons'), class: b, value: b, role: '', state: '', name: '', type: 'button'
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
def button_list
|
94
|
+
options[:buttons].presence || SimpleFormMarkdownEditor::MarkdownEditorInput.configuration.buttons
|
95
|
+
end
|
96
|
+
|
97
|
+
# ---------------------------------------------------------------------
|
98
|
+
|
99
|
+
def editor
|
100
|
+
template.content_tag :div, class: %w(editor) do
|
101
|
+
@builder.text_area(attribute_name, input_html_options).html_safe
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
def preview
|
106
|
+
template.content_tag :div, I18n.t(:loading, scope: 'simple_form_markdown_editor'), class: %w(preview), data: { :'nothing-to-preview-text' => I18n.t(:nothing_to_preview, scope: 'simple_form_markdown_editor') }
|
107
|
+
end
|
108
|
+
|
109
|
+
# ---------------------------------------------------------------------
|
110
|
+
|
111
|
+
def help
|
112
|
+
return unless help_enabled?
|
113
|
+
template.content_tag :div, class: %w(help), data: { visible: help_visible? } do
|
114
|
+
template.content_tag :div, class: %w(help_wrapper) do
|
115
|
+
help_sections + help_sub_sections + help_texts
|
116
|
+
end
|
117
|
+
end
|
118
|
+
end
|
119
|
+
|
120
|
+
def help_sections
|
121
|
+
template.content_tag :ul, class: %w(sections) do
|
122
|
+
i18n_help.map{ |section, content| help_section(section, content) }.flatten.join.html_safe
|
123
|
+
end
|
124
|
+
end
|
125
|
+
|
126
|
+
def help_section section, content
|
127
|
+
return unless content[:title]
|
128
|
+
template.content_tag :li, class: ['section', section.to_s], data: { toggle: section.to_s } do
|
129
|
+
template.content_tag :span, content[:title].to_s, class: section.to_s
|
130
|
+
end.html_safe
|
131
|
+
end
|
132
|
+
|
133
|
+
def help_sub_sections
|
134
|
+
i18n_help.map do |section, content|
|
135
|
+
template.content_tag :ul, class: ['sub_sections', section.to_s] do
|
136
|
+
content[:elements].map{ |section, content| help_sub_section(section, content) }.flatten.join.html_safe
|
137
|
+
end
|
138
|
+
end.flatten.join.html_safe
|
139
|
+
end
|
140
|
+
|
141
|
+
def help_sub_section section, content
|
142
|
+
return unless content[:title]
|
143
|
+
template.content_tag :li, class: ['sub_section', section.to_s], data: { toggle: section.to_s } do
|
144
|
+
template.content_tag :span, content[:title].to_s, class: section.to_s
|
145
|
+
end.html_safe
|
146
|
+
end
|
147
|
+
|
148
|
+
def help_texts
|
149
|
+
i18n_help.map do |section, content|
|
150
|
+
content[:elements].map do |element, content|
|
151
|
+
template.content_tag :div, class: ['help_text', element.to_s], data: { section: section.to_s, sub_section: element.to_s } do
|
152
|
+
SimpleFormMarkdownEditor::Renderer.call(content[:text])
|
153
|
+
end
|
154
|
+
end
|
155
|
+
end.flatten.join.html_safe
|
156
|
+
end
|
157
|
+
|
158
|
+
# ---------------------------------------------------------------------
|
159
|
+
|
160
|
+
def i18n_help
|
161
|
+
I18n.t(:help, scope: 'simple_form_markdown_editor')
|
162
|
+
end
|
163
|
+
|
164
|
+
def help_enabled?
|
165
|
+
enabled_in_options = options.fetch(:help, {}).fetch(:enabled, nil)
|
166
|
+
enabled_in_config = SimpleFormMarkdownEditor::MarkdownEditorInput.configuration.help.fetch(:enabled, false)
|
167
|
+
|
168
|
+
return enabled_in_config if enabled_in_options.nil?
|
169
|
+
|
170
|
+
enabled_in_options
|
171
|
+
end
|
172
|
+
|
173
|
+
def help_visible?
|
174
|
+
visible_in_options = options.fetch(:help, {}).fetch(:visible, nil)
|
175
|
+
visible_in_config = SimpleFormMarkdownEditor::MarkdownEditorInput.configuration.help.fetch(:visible, false)
|
176
|
+
|
177
|
+
return visible_in_config if visible_in_options.nil?
|
178
|
+
|
179
|
+
visible_in_options
|
180
|
+
end
|
181
|
+
|
182
|
+
end
|
183
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
require "simple_form"
|
2
|
+
|
3
|
+
require "simple_form_markdown_editor/configuration"
|
4
|
+
require "simple_form_markdown_editor/engine"
|
5
|
+
require "simple_form_markdown_editor/renderer"
|
6
|
+
require "simple_form_markdown_editor/simple_form_markdown_editor"
|
7
|
+
require "simple_form_markdown_editor/version"
|
8
|
+
|
9
|
+
require "i18n"
|
10
|
+
|
11
|
+
# ---------------------------------------------------------------------
|
12
|
+
|
13
|
+
module SimpleForm
|
14
|
+
class FormBuilder
|
15
|
+
map_type :markdown_editor, to: SimpleFormMarkdownEditor::MarkdownEditorInput
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
# ---------------------------------------------------------------------
|
20
|
+
|
21
|
+
I18n.load_path += Dir.glob(File.join( File.dirname(__FILE__), 'config', 'locales', '*.yml' ))
|
@@ -0,0 +1,30 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'simple_form_markdown_editor/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "simple_form_markdown_editor"
|
8
|
+
spec.version = SimpleFormMarkdownEditor::VERSION
|
9
|
+
spec.authors = ["Tomáš Celizna", "Asger Behncke Jacobsen"]
|
10
|
+
spec.email = ["tomas.celizna@gmail.com", "asger@8kilo.com"]
|
11
|
+
spec.summary = %q{Simple Markdown editor (inspired by GitHub editor).}
|
12
|
+
spec.description = %q{Simple Markdown editor (inspired by GitHub editor).}
|
13
|
+
spec.homepage = "https://github.com/tomasc/simple_form_markdown_editor"
|
14
|
+
spec.license = "MIT"
|
15
|
+
|
16
|
+
spec.files = `git ls-files -z`.split("\x0")
|
17
|
+
spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
|
18
|
+
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
19
|
+
spec.require_paths = ["lib"]
|
20
|
+
|
21
|
+
spec.add_dependency "rails", ">= 4.2"
|
22
|
+
spec.add_dependency "simple_form", ">= 3.0.2"
|
23
|
+
spec.add_dependency "redcarpet"
|
24
|
+
spec.add_dependency "autoprefixer-rails"
|
25
|
+
|
26
|
+
spec.add_dependency "responders", "~> 2.0"
|
27
|
+
|
28
|
+
spec.add_development_dependency "bundler", "~> 1.6"
|
29
|
+
spec.add_development_dependency "rake"
|
30
|
+
end
|