Skip to content

Commit

Permalink
Move Tinymce custom configuration to richtext editor
Browse files Browse the repository at this point in the history
Instead of a CSS class the id of the element is used to target the Tinymce textarea. Also the configuration is now in the richtext editor template.
  • Loading branch information
sascha-karnatz committed May 24, 2023
1 parent 7cbfc67 commit e0bd795
Show file tree
Hide file tree
Showing 12 changed files with 72 additions and 212 deletions.
19 changes: 12 additions & 7 deletions app/models/alchemy/ingredients/richtext.rb
Original file line number Diff line number Diff line change
Expand Up @@ -28,15 +28,23 @@ def preview_text(max_length = 30)
stripped_body.to_s[0..max_length - 1]
end

# Returns css class names for the editor textarea.
def tinymce_class_name
"has_tinymce#{has_custom_tinymce_config? ? " #{element.name}_#{role}" : ""}"
def element_id
"tinymce_#{id}"
end

def has_tinymce?
true
end

# Returns true if there is a tinymce setting defined that contains settings.
def has_custom_tinymce_config?
custom_tinymce_config.is_a?(Hash)
end

def custom_tinymce_config
settings[:tinymce]
end

private

def strip_content
Expand All @@ -54,10 +62,7 @@ def sanitizer_settings
settings[:sanitizer] || {}
end

# Returns true if there is a tinymce setting defined that contains settings.
def has_custom_tinymce_config?
settings[:tinymce].is_a?(Hash)
end

end
end
end
10 changes: 0 additions & 10 deletions app/views/alchemy/admin/pages/_tinymce_custom_config.html.erb

This file was deleted.

3 changes: 0 additions & 3 deletions app/views/alchemy/admin/pages/edit.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -138,9 +138,6 @@
<% end %>

<% content_for :javascripts do %>
<% if Alchemy::Tinymce.custom_configs_present?(@page) %>
<%= render 'tinymce_custom_config' %>
<% end %>

<% content_for :javascript_includes do %>
<meta name="turbolinks-cache-control" content="no-cache">
Expand Down
13 changes: 11 additions & 2 deletions app/views/alchemy/ingredients/_richtext_editor.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,17 @@
<%= ingredient_label(richtext_editor) %>
<div class="tinymce_container">
<%= f.text_area :value,
class: richtext_editor.tinymce_class_name,
id: "tinymce_#{richtext_editor.id}" %>
class: "has_tinymce",
id: richtext_editor.element_id %>
</div>
<% end %>
<% if richtext_editor.has_custom_tinymce_config? %>
<script type="text/javascript" charset="utf-8">
Alchemy.Tinymce.setCustomConfig("<%= richtext_editor.element_id %>", {
<% richtext_editor.custom_tinymce_config.each do |k, v| %>
<%= k %>: <%== v.to_json %>,
<% end %>
});
</script>
<% end %>
<% end %>
23 changes: 0 additions & 23 deletions lib/alchemy/tinymce.rb
Original file line number Diff line number Diff line change
Expand Up @@ -33,29 +33,6 @@ def init=(settings)
def init
@@init
end

def custom_configs_present?(page)
custom_config_ingredients(page).any?
end

def custom_config_ingredients(page)
ingredient_definitions_from_elements(page.descendent_element_definitions)
end

private

def ingredient_definitions_from_elements(definitions)
definitions.collect do |el|
next if el["ingredients"].blank?

ingredients = el["ingredients"].select do |c|
c["settings"] && c["settings"]["tinymce"].is_a?(Hash)
end
next if ingredients.blank?

ingredients.map { |c| c.merge("element" => el["name"]) }
end.flatten.compact
end
end
end
end
2 changes: 1 addition & 1 deletion package/dist/admin.js

Large diffs are not rendered by default.

6 changes: 3 additions & 3 deletions package/dist/admin.js.map

Large diffs are not rendered by default.

8 changes: 4 additions & 4 deletions package/src/tinymce.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,9 @@ function getDefaultConfig(editorId) {
// Returns configuration for given custom tinymce editor selector.
//
// It uses the +.getDefaultConfig+ and merges the custom parts.
function getConfig(id, selector) {
const editorConfig = tinymceCustomConfigs[selector] || {}
return { ...getDefaultConfig(id), ...editorConfig }
function getConfig(editorId) {
const editorConfig = tinymceCustomConfigs[editorId] || {}
return { ...getDefaultConfig(editorId), ...editorConfig }
}

// create intersection observer and register textareas to be initialized when
Expand Down Expand Up @@ -67,7 +67,7 @@ function initializeIntersectionObserver() {
// Initializes one specific TinyMCE editor
function initTinymceEditor(textarea) {
const editorId = textarea.id
const config = getConfig(editorId, textarea.classList[1])
const config = getConfig(editorId)

// remove editor instance, if already initialized
removeEditor(editorId)
Expand Down
139 changes: 0 additions & 139 deletions spec/libraries/tinymce_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -20,144 +20,5 @@ module Alchemy
expect(Tinymce.init).to include(another_config)
end
end

context "Methods for ingredients with custom tinymce config." do
let(:ingredient_definition) do
{
"role" => "text",
"settings" => {
"tinymce" => {
"foo" => "bar"
}
}
}
end

let(:element_definition) do
{
"name" => "article",
"ingredients" => [ingredient_definition]
}
end

describe ".custom_configs_present?" do
let(:page) { build_stubbed(:alchemy_page) }

subject { described_class.custom_configs_present?(page) }

context "if custom_config_ingredients are present" do
before do
expect(described_class).to receive(:custom_config_ingredients) { [:foo] }
end

it { is_expected.to be(true) }
end

context "if no custom_config_ingredients are present" do
before do
expect(described_class).to receive(:custom_config_ingredients) { [] }
end

it { is_expected.to be(false) }
end
end

describe ".custom_config_ingredients" do
let(:page) { build_stubbed(:alchemy_page) }

let(:element_definition) do
{
"name" => "article",
"ingredients" => [ingredient_definition]
}
end

let(:element_definitions) do
[element_definition]
end

let(:ingredient_definition) do
{
"role" => "text",
"settings" => {
"tinymce" => {
"foo" => "bar"
}
}
}
end

subject { Tinymce.custom_config_ingredients(page) }

before do
expect(page).to receive(:descendent_element_definitions) { element_definitions }
end

it "returns an array of ingredient definitions that contain custom tinymce config
and element name" do
is_expected.to be_an(Array)
is_expected.to include({
"element" => element_definition["name"]
}.merge(ingredient_definition))
end

context "with no ingredients having custom tinymce config" do
let(:ingredient_definition) do
{"role" => "text"}
end

it { is_expected.to eq([]) }
end

context "with element definition having nil as ingredients value" do
let(:element_definition) do
{
"name" => "element",
"ingredients" => nil
}
end

it "returns empty array" do
is_expected.to eq([])
end
end

context "with ingredient settings tinymce set to true only" do
let(:element_definition) do
{
"name" => "element",
"ingredients" => [
"role" => "headline",
"settings" => {
"tinymce" => true
}
]
}
end

it "returns empty array" do
is_expected.to eq([])
end
end

context "with nestable_elements defined" do
let(:element_definitions) do
[
element_definition,
{
"name" => "nested_element",
"ingredients" => [ingredient_definition]
}
]
end

it "includes these configs" do
is_expected.to include({
"element" => element_definition["name"]
}.merge(ingredient_definition))
end
end
end
end
end
end
39 changes: 27 additions & 12 deletions spec/models/alchemy/ingredients/richtext_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
let(:element) do
build(:alchemy_element, name: "article", autogenerate_ingredients: false)
end
let(:richtext_settings) { {} }

let(:richtext_ingredient) do
described_class.new(
Expand All @@ -18,6 +19,10 @@
)
end

before do
allow(richtext_ingredient).to receive(:settings) { richtext_settings }
end

it "has a HTML tag free version of body column" do
richtext_ingredient.save
expect(richtext_ingredient.stripped_body).to eq("Hello!Welcome to Peters Petshop.")
Expand All @@ -28,21 +33,31 @@
expect(richtext_ingredient.sanitized_body).to eq("<h1>Hello!</h1><p class=\"green\">Welcome to Peters Petshop.</p>")
end

describe "#tinymce_class_name" do
subject { richtext_ingredient.tinymce_class_name }
describe "#element_id" do
subject { richtext_ingredient.element_id }

it { is_expected.to eq("tinymce_#{richtext_ingredient.id}") }
end

describe "#has_custom_tinymce_config?" do
subject { richtext_ingredient.has_custom_tinymce_config? }

it { is_expected.to be_falsy }

context "with custom configuration" do
let(:richtext_settings) { {tinymce: {plugin: 'link'}} }
it { is_expected.to be_truthy }
end
end

it { is_expected.to eq("has_tinymce") }
describe "#custom_tinymce_config" do
subject { richtext_ingredient.custom_tinymce_config }

context "having custom tinymce config" do
before do
expect(richtext_ingredient).to receive(:settings) do
{tinymce: {toolbar: []}}
end
end
it { is_expected.to be_nil }

it "returns role including element name" do
is_expected.to eq("has_tinymce article_text")
end
context "with custom configuration" do
let(:richtext_settings) { {tinymce: {plugin: 'link'}} }
it { is_expected.to eq({plugin: 'link'}) }
end
end

Expand Down
8 changes: 0 additions & 8 deletions spec/requests/alchemy/admin/pages_controller_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -578,14 +578,6 @@ module Alchemy
expect_any_instance_of(Page).to receive(:lock_to!)
get edit_admin_page_path(page)
end

context "if custom tinymce configs are present" do
it "adds the custom config to the head" do
expect(Alchemy::Tinymce).to receive(:custom_configs_present?).with(page) { true }
get edit_admin_page_path(page)
expect(response.body).to match(/Populate custom tinymce configurations/)
end
end
end

context "if page is scoped" do
Expand Down
14 changes: 14 additions & 0 deletions spec/views/alchemy/ingredients/richtext_editor_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -21,4 +21,18 @@
it "renders a text area for tinymce" do
expect(rendered).to have_selector(".tinymce_container textarea#tinymce_#{ingredient.id}.has_tinymce")
end

context "without custom configuration" do
it "does not renders a custom configuration" do
expect(rendered).to_not have_selector(".ingredient-editor.richtext script")
end
end

context "with custom configuration" do
let(:settings) { {tinymce: {plugin: 'link'}} }

it "renders a custom configuration" do
expect(rendered).to have_selector(".ingredient-editor.richtext script")
end
end
end

0 comments on commit e0bd795

Please sign in to comment.