Skip to content

Commit 43bc855

Browse files
committed
Refactor syntax highlight form with nested turbo frame and turbo stream
1 parent a5ed60c commit 43bc855

File tree

3 files changed

+160
-96
lines changed

3 files changed

+160
-96
lines changed

app/javascript/controllers/syntax-highlight/preview.js

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,23 @@
11
import { Controller } from '@hotwired/stimulus';
22

3+
import debug from '../../utils/debug';
4+
5+
const console = debug('app:javascript:controllers:syntax-highlight:preview');
6+
7+
let submitting = false;
8+
39
export default class extends Controller {
410
static values = {
511
name: String, // The name of the syntax highlight css file to enable
612
};
713

14+
static targets = ['select'];
15+
816
connect() {
17+
console.log('connect');
18+
919
const name = this.nameValue;
20+
1021
document
1122
.querySelectorAll('link[rel="stylesheet"][data-syntax-highlight]')
1223
.forEach((link) => {
@@ -15,5 +26,19 @@ export default class extends Controller {
1526
});
1627
link.disabled = name !== link.dataset.syntaxHighlight;
1728
});
29+
30+
if (submitting) {
31+
this.selectTarget.focus();
32+
submitting = false;
33+
}
34+
}
35+
36+
change(event) {
37+
if (event.target.form) {
38+
event.target.form.requestSubmit();
39+
40+
// This is some hacky module state so that we can retain the focus on the re-rendered select element after a submit
41+
submitting = true;
42+
}
1843
}
1944
}

app/views/settings/syntax_highlights/form.rb

Lines changed: 133 additions & 94 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@ class Settings::SyntaxHighlights::Form < ApplicationView
44
include Phlex::Rails::Helpers::ButtonTo
55
include Phlex::Rails::Helpers::ContentFor
66
include Phlex::Rails::Helpers::StylesheetLinkTag
7+
include Phlex::Rails::Helpers::TurboFrameTag
8+
include Phlex::Rails::Helpers::TurboStream
79

810
def initialize(
911
settings:,
@@ -21,91 +23,45 @@ def initialize(
2123
end
2224

2325
def view_template
24-
stylesheet_link_tag @current_highlight.asset_path, data: {syntax_highlight: @current_highlight.name}
25-
2626
div(
27-
class: "grid grid-content",
28-
data: {
29-
controller: "syntax-highlight-preview",
30-
syntax_highlight_preview_name_value: @current_highlight.name
31-
}
27+
class: "grid grid-content"
3228
) do
3329
h2 { "Want to preview a new syntax highlighting theme?" }
3430

3531
markdown do
3632
"This site uses [Pygments-style CSS](https://pygments.org/) for syntax highlighting. You can use the select menu to preview a new syntax highlighting theme. I have curated over 90 options for you from sources around the web."
3733
end
3834

39-
if previewing?
40-
markdown do
41-
"You are currently previewing **#{@current_highlight.display_name}** as your syntax highlighting theme."
42-
end
43-
end
44-
45-
if preserving?
46-
markdown do
47-
"You have saved **#{@session_syntax_highlight.display_name}** for syntax highlighting across the site."
48-
end
49-
end
5035
preview_select
5136

52-
if previewing?
53-
markdown do
54-
"You can preview what the site looks with this syntax highlighting theme while you remain on this page. Click the **Reset preview** button to go back to #{@session_syntax_highlight ? "your saved color scheme, **#{@session_syntax_highlight.display_name}**" : "the default color scheme, **#{@default_syntax_highlight.display_name}**"}."
55-
end
56-
57-
div(class: "outside") { reset_button }
37+
h2 { %(Preview) }
5838

59-
darkmode_section
39+
markdown do
40+
"You can preview what the site looks with this syntax highlighting theme while you remain on this page."
41+
end
6042

61-
markdown do
62-
"Click the Save button to preserve **#{@current_highlight.display_name}** as your new syntax highlighting theme."
43+
flex_list do
44+
div do
45+
h3 { %(Ruby) }
46+
render CodeBlock::AppFile.new("app/models/examples/counter.rb", language: "rb")
6347
end
64-
65-
div(class: "outside") do
66-
button_to("Save #{@current_highlight.display_name}",
67-
settings_syntax_highlight_path(settings: {syntax_highlight_name: @current_highlight.name}),
68-
method: :patch,
69-
class: "button primary")
48+
div do
49+
h3 { %(CSS) }
50+
render CodeBlock::AppFile.new("app/javascript/css/components/site-header.css", language: "css")
7051
end
71-
end
72-
73-
h2 { %(Preview) }
74-
75-
h3 { %(Ruby) }
76-
77-
render CodeBlock::Article.new(language: "ruby") do |code|
78-
code.body do
79-
<<~RUBY.html_safe
80-
class Family < Group
81-
include Enumerable
82-
83-
def initialize(*members)
84-
@members = members
85-
end
86-
87-
def each(&)
88-
@members.each(&)
89-
end
90-
end
91-
RUBY
52+
div do
53+
h3 { %(JavaScript) }
54+
render CodeBlock::AppFile.new("app/javascript/controllers/application.js", language: "js")
9255
end
93-
end
94-
h3 { %(CSS) }
95-
render CodeBlock::Article.new(language: "css") do |code|
96-
code.body do
97-
<<~CSS
98-
body {
99-
font-size: 12pt;
100-
background: #fff url(temp.png) top left no-repeat;
101-
}
102-
CSS
56+
div do
57+
h3 { %(HTML with ERB) }
58+
render CodeBlock::AppFile.new("app/views/examples/counters/show.html.erb", language: "erb")
10359
end
10460
end
105-
h3 { %(JavaScript) }
106-
render CodeBlock::AppFile.new("app/javascript/controllers/syntax-highlight/preview.js", language: "js")
107-
h3 { %(HTML with ERB) }
108-
render CodeBlock::AppFile.new("app/views/layouts/application.html.erb", language: "erb")
61+
end
62+
63+
div(id: "syntax-highlight-preview-results", class: "grid grid-content") do
64+
preview_result
10965
end
11066
end
11167

@@ -117,51 +73,114 @@ def darkmode_section
11773
end
11874

11975
markdown do
120-
"You can toggle the dark mode switch to see how the syntax highlighting looks in light or dark mode. Choosing **Light Mode** or **Dark Mode** will save in your browser local storage and will persist across page views on your current device. Choose **System Mode** to remove the saved choice and fall back to your system preference."
76+
"Toggle this switch to see the syntax highlighting when the _site_ is Light or Dark Mode. Choosing **Light Mode** or **Dark Mode** will save in your browser local storage and will persist across page views on your current device. Choose **System Mode** to remove the saved choice and fall back to your system preference."
12177
end
12278
div(class: "outside") do
12379
render "darkmode/switch", enable_description: true, enable_outline: true
12480
end
12581
end
12682

127-
private
83+
def preview_select
84+
turbo_frame_tag "syntax-highlight-preview" do
85+
stylesheet_link_tag @current_highlight.asset_path, data: {syntax_highlight: @current_highlight.name}
86+
87+
form_with(
88+
model: @settings,
89+
url: settings_syntax_highlight_path,
90+
method: :get,
91+
data: {
92+
controller: "syntax-highlight-preview",
93+
syntax_highlight_preview_name_value: @current_highlight.name,
94+
turbo_action: "advance"
95+
}
96+
) do |form|
97+
fieldset do
98+
flex_block do
99+
form.label :syntax_highlight_name, "Choose another syntax highlighting theme to preview:"
100+
form.select :syntax_highlight_name,
101+
syntax_highlight_options_for_select,
102+
{
103+
selected: @current_highlight.name,
104+
autocomplete: "off"
105+
},
106+
data: {
107+
syntax_highlight_preview_target: "select",
108+
action: "change->syntax-highlight-preview#change"
109+
}
110+
end
111+
end
112+
end
128113

129-
def previewing? = @preview_syntax_highlight.present?
114+
turbo_stream.update "syntax-highlight-preview-results" do
115+
preview_result
116+
end
117+
end
118+
end
130119

131-
def preserving? = @session_syntax_highlight.present?
120+
def preview_result
121+
if default?
122+
h2 { "Your syntax highlighting theme" }
132123

133-
def markdown
134-
render Markdown::Application.new(yield)
135-
end
124+
markdown do
125+
"You are currently using the default syntax highlighting theme, **#{@default_syntax_highlight.display_name}** as your syntax highlighting theme."
126+
end
136127

137-
def m
138-
Markdown::Application.new(yield).call.html_safe
139-
end
128+
darkmode_section
140129

141-
def preview_select
142-
form_with(
143-
model: @settings,
144-
url: settings_syntax_highlight_path,
145-
method: :get
146-
) do |form|
147-
fieldset do
148-
flex_block do
149-
form.label :syntax_highlight_name, "Choose another syntax highlighting theme to preview:"
150-
form.select :syntax_highlight_name,
151-
syntax_highlight_options_for_select,
152-
{
153-
selected: @current_highlight.name
154-
},
155-
onchange: "this.form.requestSubmit()"
156-
end
130+
return
131+
end
132+
133+
if previewing?
134+
h2 { "Save your preview" }
135+
136+
markdown do
137+
"You are currently previewing **#{@current_highlight.display_name}** as your syntax highlighting theme."
138+
end
139+
140+
darkmode_section
141+
142+
markdown do
143+
"Click the Save button to preserve **#{@current_highlight.display_name}** as your new syntax highlighting theme. Your choice will be saved in your browser session."
144+
end
145+
146+
div(class: "outside") do
147+
button_to("Save #{@current_highlight.display_name}",
148+
settings_syntax_highlight_path(settings: {syntax_highlight_name: @current_highlight.name}),
149+
method: :patch,
150+
class: "button primary")
151+
end
152+
153+
markdown do
154+
"Click the **Reset preview** button to go back to #{@session_syntax_highlight ? "your saved color scheme, **#{@session_syntax_highlight.display_name}**" : "the default color scheme, **#{@default_syntax_highlight.display_name}**"}."
155+
end
156+
157+
div(class: "outside") { reset_button }
158+
end
159+
160+
if preserving?
161+
h2 { "Your syntax highlighting theme" }
162+
163+
markdown do
164+
"You have saved **#{@session_syntax_highlight.display_name}** for syntax highlighting across the site."
157165
end
166+
167+
darkmode_section if !previewing?
168+
169+
markdown do
170+
"You can delete #{@session_syntax_highlight.display_name} your saved syntax highlighting theme and go back to the default."
171+
end
172+
div(class: "outside") { unsave_button }
158173
end
159174
end
160175

161176
def flex_block(options = {}, &)
162177
div(class: "flex items-start flex-col space-col-4 grid-cols-12 md:items-center md:flex-row md:space-row-4 #{options[:class]}", &)
163178
end
164179

180+
def flex_list(options = {}, &)
181+
div(class: "code-examples--list flex items-start flex-col space-col-4 grid-cols-12 md:flex-row md:space-row-4 #{options[:class]}", &)
182+
end
183+
165184
def syntax_highlight_options_for_select
166185
@available_highlights
167186
.group_by { |sh| sh.mode }
@@ -173,4 +192,24 @@ def reset_button
173192
url_for,
174193
class: "button tertiary"
175194
end
195+
196+
def unsave_button
197+
button_to "Delete my syntax highlighting choice",
198+
settings_syntax_highlight_path(settings: {syntax_highlight_name: @default_syntax_highlight.name}),
199+
method: :patch,
200+
class: "button warn",
201+
style: "min-width: 25ch;"
202+
end
203+
204+
private
205+
206+
def previewing? = @preview_syntax_highlight.present?
207+
208+
def preserving? = @session_syntax_highlight.present?
209+
210+
def default? = @current_highlight == @default_syntax_highlight
211+
212+
def markdown
213+
render Markdown::Application.new(yield)
214+
end
176215
end

app/views/settings/syntax_highlights/show_view.rb

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,8 @@ def initialize(
1818
def view_template
1919
render Pages::Header.new(title: "Settings: Syntax Highlighting")
2020

21-
section(class: %(secton-content container py-gap)) do
22-
turbo_frame_tag "syntax-highlight-form", data: {turbo_action: "advance"} do
21+
section(class: %(section-content container py-gap)) do
22+
turbo_frame_tag "syntax-highlight-form" do
2323
render Settings::SyntaxHighlights::Form.new(
2424
settings: @settings,
2525
available_highlights: @available_highlights,

0 commit comments

Comments
 (0)