alchemy_cms 4.1.2 → 4.2.0.rc1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (155) hide show
  1. checksums.yaml +4 -4
  2. data/.github/ISSUE_TEMPLATE/Bug_report.md +0 -5
  3. data/.rubocop.yml +4 -1
  4. data/.travis.yml +3 -3
  5. data/CHANGELOG.md +29 -10
  6. data/Gemfile +5 -7
  7. data/README.md +114 -62
  8. data/Rakefile +2 -2
  9. data/alchemy_cms.gemspec +5 -5
  10. data/app/assets/images/alchemy/icon.svg +1 -1
  11. data/app/assets/javascripts/alchemy/admin.js +2 -0
  12. data/app/assets/javascripts/alchemy/alchemy.base.js.coffee +0 -24
  13. data/app/assets/javascripts/alchemy/alchemy.datepicker.js.coffee +11 -9
  14. data/app/assets/javascripts/alchemy/alchemy.dragndrop.js.coffee +7 -24
  15. data/app/assets/javascripts/alchemy/alchemy.element_editors.js.coffee +9 -8
  16. data/app/assets/javascripts/alchemy/alchemy.fixed_elements.js +38 -0
  17. data/app/assets/javascripts/alchemy/alchemy.sitemap.js.coffee +2 -4
  18. data/app/assets/javascripts/alchemy/alchemy.translations.js.coffee +1 -1
  19. data/app/assets/stylesheets/alchemy/_mixins.scss +2 -1
  20. data/app/assets/stylesheets/alchemy/_variables.scss +7 -2
  21. data/app/assets/stylesheets/alchemy/admin.scss +2 -1
  22. data/app/assets/stylesheets/alchemy/archive.scss +18 -4
  23. data/app/assets/stylesheets/alchemy/buttons.scss +1 -1
  24. data/app/assets/stylesheets/alchemy/dialogs.scss +1 -1
  25. data/app/assets/stylesheets/alchemy/elements.scss +154 -90
  26. data/app/assets/stylesheets/alchemy/filter_field.scss +30 -0
  27. data/app/assets/stylesheets/alchemy/flatpickr.scss +839 -0
  28. data/app/assets/stylesheets/alchemy/forms.scss +5 -1
  29. data/app/assets/stylesheets/alchemy/frame.scss +6 -14
  30. data/app/assets/stylesheets/alchemy/navigation.scss +109 -98
  31. data/app/assets/stylesheets/alchemy/search.scss +11 -29
  32. data/app/assets/stylesheets/alchemy/tables.scss +0 -23
  33. data/app/assets/stylesheets/alchemy/tags.scss +4 -27
  34. data/app/assets/stylesheets/alchemy/toolbar.scss +12 -2
  35. data/app/assets/stylesheets/tinymce/skins/alchemy/skin.min.css.scss +4 -33
  36. data/app/controllers/alchemy/admin/attachments_controller.rb +1 -12
  37. data/app/controllers/alchemy/admin/contents_controller.rb +2 -24
  38. data/app/controllers/alchemy/admin/elements_controller.rb +11 -49
  39. data/app/controllers/alchemy/admin/pages_controller.rb +1 -1
  40. data/app/controllers/alchemy/admin/pictures_controller.rb +1 -14
  41. data/app/controllers/alchemy/api/contents_controller.rb +1 -1
  42. data/app/controllers/alchemy/api/elements_controller.rb +1 -1
  43. data/app/controllers/alchemy/api/pages_controller.rb +1 -1
  44. data/app/controllers/concerns/alchemy/admin/archive_overlay.rb +20 -0
  45. data/app/helpers/alchemy/admin/base_helper.rb +8 -18
  46. data/app/helpers/alchemy/admin/elements_helper.rb +55 -85
  47. data/app/helpers/alchemy/admin/pictures_helper.rb +0 -23
  48. data/app/helpers/alchemy/elements_helper.rb +80 -120
  49. data/app/helpers/alchemy/pages_helper.rb +5 -24
  50. data/app/models/alchemy/content.rb +0 -1
  51. data/app/models/alchemy/content/factory.rb +33 -57
  52. data/app/models/alchemy/element.rb +46 -66
  53. data/app/models/alchemy/element/element_contents.rb +2 -2
  54. data/app/models/alchemy/page.rb +34 -4
  55. data/app/models/alchemy/page/page_elements.rb +30 -122
  56. data/app/serializers/alchemy/attachment_serializer.rb +0 -2
  57. data/app/serializers/alchemy/content_serializer.rb +0 -2
  58. data/app/serializers/alchemy/element_serializer.rb +0 -3
  59. data/app/serializers/alchemy/essence_boolean_serializer.rb +0 -2
  60. data/app/serializers/alchemy/essence_date_serializer.rb +0 -2
  61. data/app/serializers/alchemy/essence_file_serializer.rb +0 -2
  62. data/app/serializers/alchemy/essence_html_serializer.rb +0 -2
  63. data/app/serializers/alchemy/essence_link_serializer.rb +0 -2
  64. data/app/serializers/alchemy/essence_picture_serializer.rb +0 -2
  65. data/app/serializers/alchemy/essence_richtext_serializer.rb +0 -2
  66. data/app/serializers/alchemy/essence_select_serializer.rb +0 -2
  67. data/app/serializers/alchemy/essence_text_serializer.rb +0 -2
  68. data/app/serializers/alchemy/legacy_element_serializer.rb +0 -3
  69. data/app/serializers/alchemy/page_serializer.rb +2 -8
  70. data/app/serializers/alchemy/page_tree_serializer.rb +1 -1
  71. data/app/serializers/alchemy/picture_serializer.rb +0 -2
  72. data/app/views/alchemy/admin/clipboard/index.html.erb +2 -2
  73. data/app/views/alchemy/admin/clipboard/insert.js.erb +9 -12
  74. data/app/views/alchemy/admin/contents/create.js.erb +4 -30
  75. data/app/views/alchemy/admin/elements/_element.html.erb +27 -12
  76. data/app/views/alchemy/admin/elements/_element_toolbar.html.erb +1 -1
  77. data/app/views/alchemy/admin/elements/_new_element_form.html.erb +0 -10
  78. data/app/views/alchemy/admin/elements/create.js.erb +12 -12
  79. data/app/views/alchemy/admin/elements/fold.js.erb +1 -1
  80. data/app/views/alchemy/admin/elements/index.html.erb +20 -19
  81. data/app/views/alchemy/admin/elements/publish.js.erb +5 -0
  82. data/app/views/alchemy/admin/elements/trash.js.erb +4 -1
  83. data/app/views/alchemy/admin/essence_pictures/assign.js.erb +0 -7
  84. data/app/views/alchemy/admin/essence_pictures/destroy.js.erb +0 -22
  85. data/app/views/alchemy/admin/pages/_publication_fields.html.erb +2 -4
  86. data/app/views/alchemy/admin/pages/edit.html.erb +1 -1
  87. data/app/views/alchemy/admin/pages/index.html.erb +14 -10
  88. data/app/views/alchemy/admin/partials/_language_tree_select.html.erb +1 -1
  89. data/app/views/alchemy/admin/partials/_main_navigation_entry.html.erb +1 -1
  90. data/app/views/alchemy/admin/partials/_remote_search_form.html.erb +7 -5
  91. data/app/views/alchemy/admin/partials/_routes.html.erb +0 -1
  92. data/app/views/alchemy/admin/partials/_search_form.html.erb +6 -4
  93. data/app/views/alchemy/admin/pictures/_picture_to_assign.html.erb +6 -3
  94. data/app/views/alchemy/admin/pictures/index.html.erb +1 -1
  95. data/app/views/alchemy/admin/trash/index.html.erb +8 -7
  96. data/app/views/alchemy/elements/_editor_not_found.html.erb +1 -1
  97. data/app/views/alchemy/essences/_essence_picture_editor.html.erb +4 -19
  98. data/app/views/layouts/alchemy/admin.html.erb +1 -0
  99. data/bin/rspec +0 -5
  100. data/config/alchemy/config.yml +3 -0
  101. data/config/brakeman.ignore +1 -1
  102. data/config/locales/alchemy.en.yml +6 -12
  103. data/config/routes.rb +1 -5
  104. data/db/migrate/20180226123013_alchemy_four_point_zero.rb +0 -29
  105. data/db/migrate/20180519204655_add_fixed_to_alchemy_elements.rb +6 -0
  106. data/lib/alchemy/admin/locale.rb +1 -1
  107. data/lib/alchemy/cache_digests/template_tracker.rb +4 -27
  108. data/lib/alchemy/elements_finder.rb +111 -0
  109. data/lib/alchemy/errors.rb +0 -4
  110. data/lib/alchemy/modules.rb +49 -18
  111. data/lib/alchemy/tasks/tidy.rb +3 -40
  112. data/lib/alchemy/test_support/controller_requests.rb +1 -1
  113. data/lib/alchemy/test_support/essence_shared_examples.rb +1 -1
  114. data/lib/alchemy/test_support/factories/attachment_factory.rb +5 -3
  115. data/lib/alchemy/test_support/factories/content_factory.rb +4 -4
  116. data/lib/alchemy/test_support/factories/dummy_user_factory.rb +5 -5
  117. data/lib/alchemy/test_support/factories/element_factory.rb +12 -7
  118. data/lib/alchemy/test_support/factories/essence_text_factory.rb +1 -1
  119. data/lib/alchemy/test_support/factories/language_factory.rb +13 -13
  120. data/lib/alchemy/test_support/factories/page_factory.rb +18 -17
  121. data/lib/alchemy/test_support/factories/picture_factory.rb +6 -4
  122. data/lib/alchemy/test_support/factories/site_factory.rb +6 -6
  123. data/lib/alchemy/tinymce.rb +1 -1
  124. data/lib/alchemy/upgrader/four_point_two.rb +68 -0
  125. data/lib/alchemy/upgrader/tasks/cells_migration.rb +41 -0
  126. data/lib/alchemy/upgrader/tasks/cells_upgrader.rb +146 -0
  127. data/lib/alchemy/upgrader/tasks/picture_gallery_migration.rb +65 -0
  128. data/lib/alchemy/upgrader/tasks/picture_gallery_upgrader.rb +195 -0
  129. data/lib/alchemy/version.rb +1 -1
  130. data/lib/alchemy_cms.rb +1 -0
  131. data/lib/rails/generators/alchemy/elements/elements_generator.rb +1 -0
  132. data/lib/rails/generators/alchemy/elements/templates/editor.html.erb +0 -3
  133. data/lib/rails/generators/alchemy/elements/templates/editor.html.haml +0 -3
  134. data/lib/rails/generators/alchemy/elements/templates/editor.html.slim +0 -3
  135. data/lib/rails/generators/alchemy/elements/templates/view.html.erb +3 -14
  136. data/lib/rails/generators/alchemy/elements/templates/view.html.haml +3 -10
  137. data/lib/rails/generators/alchemy/elements/templates/view.html.slim +3 -10
  138. data/lib/tasks/alchemy/tidy.rake +1 -23
  139. data/lib/tasks/alchemy/upgrade.rake +44 -1
  140. data/vendor/assets/javascripts/flatpickr/flatpickr.min.js +2 -0
  141. data/vendor/assets/javascripts/tinymce/license.txt +0 -0
  142. data/vendor/assets/javascripts/tinymce/tinymce.min.js +2 -2
  143. metadata +25 -31
  144. data/app/assets/stylesheets/alchemy/jquery.datetimepicker.scss +0 -478
  145. data/app/models/alchemy/cell.rb +0 -95
  146. data/app/models/alchemy/page/page_cells.rb +0 -69
  147. data/app/serializers/alchemy/cell_serializer.rb +0 -19
  148. data/app/views/alchemy/admin/contents/new.html.erb +0 -11
  149. data/app/views/alchemy/admin/contents/order.js.erb +0 -3
  150. data/app/views/alchemy/admin/elements/_add_picture.html.erb +0 -14
  151. data/app/views/alchemy/admin/elements/_picture_gallery_editor.html.erb +0 -24
  152. data/bin/spring +0 -16
  153. data/lib/alchemy/test_support/factories/cell_factory.rb +0 -9
  154. data/vendor/assets/javascripts/date-formatter.js +0 -161
  155. data/vendor/assets/javascripts/jquery_plugins/jquery.datetimepicker.full.min.js +0 -2
data/Rakefile CHANGED
@@ -50,12 +50,12 @@ BASH
50
50
  end
51
51
 
52
52
  namespace :changelog do
53
- desc "Update CHANGELOG from GitHub (Set GITHUB_ACCESS_TOKEN and PREVIOUS_VERSION to a version you want to write changelog changes for)"
53
+ desc "Update changelog"
54
54
  task :update do
55
55
  original_file = './CHANGELOG.md'
56
56
  new_file = original_file + '.new'
57
57
  backup = original_file + '.old'
58
- changes = `git rev-list v#{ENV['PREVIOUS_VERSION']}..HEAD | bundle exec github_fast_changelog AlchemyCMS/alchemy_cms`
58
+ changes = `git rev-list v#{ENV['PREVIOUS_VERSION']}...master | bundle exec github_fast_changelog AlchemyCMS/alchemy_cms`
59
59
  File.open(new_file, 'w') do |fo|
60
60
  fo.puts changes
61
61
  File.foreach(original_file) do |li|
@@ -10,15 +10,15 @@ Gem::Specification.new do |gem|
10
10
  gem.authors = ['Thomas von Deyen', 'Robin Boening', 'Marc Schettke', 'Hendrik Mans', 'Carsten Fregin', 'Martin Meyerhoff']
11
11
  gem.email = ['alchemy@magiclabs.de']
12
12
  gem.homepage = 'https://alchemy-cms.com'
13
- gem.summary = 'A powerful, userfriendly and flexible CMS for Rails 4'
14
- gem.description = 'Alchemy is a powerful, userfriendly and flexible Rails 4 CMS.'
13
+ gem.summary = 'A powerful, userfriendly and flexible CMS for Rails 5'
14
+ gem.description = 'Alchemy is a powerful, userfriendly and flexible Rails 5 CMS.'
15
15
  gem.requirements << 'ImageMagick (libmagick), v6.6 or greater.'
16
- gem.required_ruby_version = '>= 2.2.2'
16
+ gem.required_ruby_version = '>= 2.3.0'
17
17
  gem.license = 'BSD New'
18
18
  gem.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^spec/}) }
19
19
  gem.require_paths = ['lib']
20
20
 
21
- gem.add_runtime_dependency 'active_model_serializers', ['~> 0.9.0']
21
+ gem.add_runtime_dependency 'active_model_serializers', ['~> 0.10.0']
22
22
  gem.add_runtime_dependency 'acts_as_list', ['~> 0.3']
23
23
  gem.add_runtime_dependency 'awesome_nested_set', ['~> 3.1']
24
24
  gem.add_runtime_dependency 'cancancan', ['~> 2.1']
@@ -33,7 +33,7 @@ Gem::Specification.new do |gem|
33
33
  gem.add_runtime_dependency 'originator', ['~> 3.1']
34
34
  gem.add_runtime_dependency 'non-stupid-digest-assets', ['~> 1.0.8']
35
35
  gem.add_runtime_dependency 'rails', ['~> 5.0', '< 6.0']
36
- gem.add_runtime_dependency 'ransack', ['>= 1.8', '< 3.0']
36
+ gem.add_runtime_dependency 'ransack', ['~> 2.0']
37
37
  gem.add_runtime_dependency 'request_store', ['~> 1.2']
38
38
  gem.add_runtime_dependency 'responders', ['~> 2.0']
39
39
  gem.add_runtime_dependency 'select2-rails', ['>= 3.5.9.1', '< 4.0']
@@ -1 +1 @@
1
- <svg xmlns="http://www.w3.org/2000/svg" viewBox="-4 -6 32 32" class="svg-inline--fa fa-lg fa-fw"><path fill="currentColor" d="M15.7 7.9L9.9 2.2 2.1 4.3 0 12.1l5.7 5.8 7.8-2.1 2.2-7.9zm-5.3 10.3l-1.2 4.4 3.2 3.2 4.4-1.2 1.2-4.4-3.2-3.2-4.4 1.2zM23.5 7.3L17.2 9l-1.7 6.2 4.5 4.6 6.2-1.7 1.7-6.2-4.4-4.6z"/></svg>
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="-2 -6 32 32" class="svg-inline--fa fa-lg fa-fw"><path fill="currentColor" d="M15.7 7.9L9.9 2.2 2.1 4.3 0 12.1l5.7 5.8 7.8-2.1 2.2-7.9zm-5.3 10.3l-1.2 4.4 3.2 3.2 4.4-1.2 1.2-4.4-3.2-3.2-4.4 1.2zM23.5 7.3L17.2 9l-1.7 6.2 4.5 4.6 6.2-1.7 1.7-6.2-4.4-4.6z"/></svg>
@@ -9,6 +9,7 @@
9
9
  //= require jquery-ui/widgets/tabs
10
10
  //= require tinymce/tinymce.min
11
11
  //= require_tree ../../../../vendor/assets/javascripts/jquery_plugins/
12
+ //= require flatpickr/flatpickr.min
12
13
  //= require clipboard.min
13
14
  //= require keymaster
14
15
  //= require requestAnimationFrame
@@ -27,6 +28,7 @@
27
28
  //= require alchemy/alchemy.dragndrop
28
29
  //= require alchemy/alchemy.element_editors
29
30
  //= require alchemy/alchemy.elements_window
31
+ //= require alchemy/alchemy.fixed_elements
30
32
  //= require alchemy/alchemy.growler
31
33
  //= require alchemy/alchemy.gui
32
34
  //= require alchemy/alchemy.hotkeys
@@ -76,30 +76,6 @@ $.extend Alchemy,
76
76
  dropdownAutoWidth: true
77
77
  return
78
78
 
79
- # Selects cell tab for given name.
80
- # Creates it if it's not present yet.
81
- selectOrCreateCellTab: (cell_name, label) ->
82
- $cells = $('#cells')
83
- $tab = $("#cell_#{cell_name}")
84
- if $tab.length == 0
85
- $("<li><a href=\"#cell_#{cell_name}\">#{label}</a></li>")
86
- .appendTo('#cells .ui-tabs-nav')
87
- $tab = $("<div id=\"cell_#{cell_name}\" class=\"sortable_cell\"/>")
88
- $cells.append($tab)
89
- $cells.tabs().tabs('refresh')
90
- $cells.tabs().tabs('option', 'active', $('#cells > div').index($tab))
91
- return
92
-
93
- # Inits the cell tabs
94
- buildTabbedCells: (label) ->
95
- $cells = $('<div id="cells"/>')
96
- $('#cell_for_other_elements').wrap($cells)
97
- $('#cells').prepend("<ul><li><a href=\"#cell_for_other_elements\">#{label}</a></li></ul>")
98
- .tabs 'paging',
99
- follow: true
100
- followOnSelect: true
101
- return
102
-
103
79
  # Logs exception to js console, if present.
104
80
  debug: (e) ->
105
81
  if window["console"]
@@ -3,7 +3,6 @@ window.Alchemy = {} if typeof(window.Alchemy) is 'undefined'
3
3
  $.extend Alchemy,
4
4
 
5
5
  Datepicker: (scope) ->
6
- $.datetimepicker.setLocale(Alchemy.locale);
7
6
  $datepicker_inputs = $('input[data-datepicker-type]', scope)
8
7
 
9
8
  # Initializes the datepickers on the text inputs and sets the proper type
@@ -15,13 +14,16 @@ $.extend Alchemy,
15
14
  $datepicker_inputs.each ->
16
15
  type = $(this).data('datepicker-type')
17
16
  options =
18
- scrollInput: false
19
- format: Alchemy.t("formats.#{type}")
20
- timepicker: /time/.test(type)
21
- datepicker: /date/.test(type)
22
- dayOfWeekStart: Alchemy.t('formats.start_of_week')
23
- onSelectDate: ->
24
- Alchemy.setElementDirty $(this).closest(".element-editor")
25
- $(this).datetimepicker(options)
17
+ # alchemy_i18n supports `zh_CN` etc., but flatpickr only has two-letter codes (`zh`)
18
+ locale: Alchemy.locale.slice(0, 2)
19
+ altInput: true
20
+ altFormat: Alchemy.t("formats.#{type}")
21
+ altInputClass: ""
22
+ enableTime: /time/.test(type)
23
+ noCalendar: type == "time"
24
+ time_24hr: Alchemy.t("formats.time_24hr")
25
+ onValueUpdate: (_selectedDates, _dateStr, instance) ->
26
+ Alchemy.setElementDirty $(instance.element).closest(".element-editor")
27
+ $(this).flatpickr(options)
26
28
 
27
29
  return
@@ -5,7 +5,7 @@ window.Alchemy = {} if typeof (window.Alchemy) is "undefined"
5
5
 
6
6
  $.extend Alchemy,
7
7
 
8
- SortableElements: (page_id, form_token, selector = '#element_area .sortable_cell') ->
8
+ SortableElements: (page_id, form_token, selector = '#element_area .sortable-elements') ->
9
9
  Alchemy.initializedSortableElements = false
10
10
  $sortable_area = $(selector)
11
11
 
@@ -25,7 +25,7 @@ $.extend Alchemy,
25
25
  opacity: 0.5
26
26
  cursor: "move"
27
27
  containment: $('#element_area')
28
- tolerance: "intersect"
28
+ tolerance: "pointer"
29
29
  update: (event, ui) ->
30
30
  # This callback is called twice for both elements, the source and the receiving
31
31
  # but, we only want to call ajax callback once on the receiving element.
@@ -35,14 +35,11 @@ $.extend Alchemy,
35
35
  Alchemy.initializedSortableElements = true
36
36
  element_ids = $.map $this.children(), (child) ->
37
37
  $(child).attr("data-element-id")
38
- cell_id = $this.data("cell-id")
39
38
  parent_element_id = ui.item.parent().closest("[data-element-id]").data('element-id')
40
39
  params =
41
40
  page_id: page_id
42
41
  authenticity_token: encodeURIComponent(form_token)
43
42
  element_ids: element_ids
44
- if cell_id?
45
- params['cell_id'] = cell_id
46
43
  if parent_element_id?
47
44
  params['parent_element_id'] = parent_element_id
48
45
  $(event.target).css("cursor", "progress")
@@ -63,6 +60,10 @@ $.extend Alchemy,
63
60
  $this.sortable('option', 'connectWith', $dropzone)
64
61
  $this.sortable('refresh')
65
62
  $dropzone.css('minHeight', 36)
63
+ ui.item.addClass('dragged')
64
+ if ui.item.hasClass('compact')
65
+ ui.placeholder.addClass('compact').css
66
+ height: ui.item.outerHeight()
66
67
  Alchemy.Tinymce.remove(ids)
67
68
  return
68
69
  stop: (event, ui) ->
@@ -70,6 +71,7 @@ $.extend Alchemy,
70
71
  name = ui.item.data('element-name')
71
72
  $dropzone = $("[data-droppable-elements~='#{name}']")
72
73
  $dropzone.css('minHeight', '')
74
+ ui.item.removeClass('dragged')
73
75
  Alchemy.Tinymce.init(ids)
74
76
  return
75
77
 
@@ -77,25 +79,6 @@ $.extend Alchemy,
77
79
  $sortable_area.find('.nested-elements').sortable(sortable_options)
78
80
  return
79
81
 
80
- SortableContents: (selector, token) ->
81
- $(selector).sortable
82
- items: "div.draggable_picture"
83
- handle: "div.picture_handle"
84
- opacity: 0.5
85
- cursor: "move"
86
- tolerance: "pointer"
87
- containment: "parent"
88
- update: (event, ui) ->
89
- ids = $.map $(this).children("div.draggable_picture"), (child) ->
90
- child.id.replace /essence_picture_/, ""
91
- $(event.originalTarget).css "cursor", "progress"
92
- $.ajax
93
- url: Alchemy.routes.order_admin_contents_path
94
- type: "POST"
95
- data: "authenticity_token=" + encodeURIComponent(token) + "&" + $.param(content_ids: ids)
96
- complete: ->
97
- $(event.originalTarget).css "cursor", "move"
98
-
99
82
  DraggableTrashItems: ->
100
83
  $("#trash_items div.draggable").each ->
101
84
  $this = $(this)
@@ -55,12 +55,12 @@ Alchemy.ElementEditors =
55
55
  # Selects element
56
56
  # Scrolls to element
57
57
  # Unfold if folded
58
- # Also chooses the right cell, if necessary.
58
+ # Also chooses the right fixed elements tab, if necessary.
59
59
  # Can be triggered through custom event 'FocusElementEditor.Alchemy'
60
60
  # Used by the elements on click events in the preview frame.
61
61
  focusElement: ($element) ->
62
62
  element_id = $element.attr('id').replace(/\D/g, "")
63
- @selectCellForElement($element)
63
+ @selectTabForElement($element)
64
64
  # If we have folded parents we need to unfold each of them
65
65
  # and then finally scroll to or unfold ourself
66
66
  $folded_parents = $element.parents('.element-editor.folded')
@@ -72,12 +72,12 @@ Alchemy.ElementEditors =
72
72
  @scrollToOrUnfold(element_id)
73
73
  return
74
74
 
75
- # Select cell for given element
76
- selectCellForElement: ($element) ->
77
- $cells = $("#cells .sortable_cell")
78
- if $cells.size() > 0
79
- $cell = $element.closest(".sortable_cell")
80
- $("#cells").tabs("option", "active", $cells.index($cell))
75
+ # Selects tab for given element
76
+ selectTabForElement: ($element) ->
77
+ $tabs = $("#fixed-elements .sortable-elements")
78
+ if $tabs.size() > 0
79
+ $tab = $element.closest(".sortable-elements")
80
+ $("#fixed-elements").tabs("option", "active", $tabs.index($tab))
81
81
 
82
82
  # Marks an element as selected in the element window and scrolls to it.
83
83
  #
@@ -117,6 +117,7 @@ Alchemy.ElementEditors =
117
117
  #
118
118
  scrollToElement: (el) ->
119
119
  $("#element_area").scrollTo el,
120
+ axis: 'y',
120
121
  duration: 400
121
122
  offset: -6
122
123
 
@@ -0,0 +1,38 @@
1
+ window.Alchemy = Alchemy || {};
2
+
3
+ Alchemy.FixedElements = {
4
+ WRAPPER: '<div id="fixed-elements"></div>',
5
+ TABS: '<ul><li><a href="#main-content-elements">{{label}}</a></li></ul>',
6
+
7
+ // Builds fixed elements tabs
8
+ buildTabs: function(label) {
9
+ var $wrapper = $(this.WRAPPER),
10
+ $tabs = $(this.TABS.replace(/{{label}}/, label));
11
+
12
+ $('#main-content-elements').wrap($wrapper);
13
+ $('#fixed-elements').prepend($tabs).tabs('paging', {
14
+ follow: true,
15
+ followOnSelect: true
16
+ });
17
+ },
18
+
19
+ // Creates a fixed element tab.
20
+ createTab: function(element_id, label) {
21
+ var $fixed_elements = $('#fixed-elements'),
22
+ $tab;
23
+
24
+ $('> ul', $fixed_elements).append('<li><a href="#fixed-element-' + element_id + '">' + label + '</a></li>');
25
+ $tab = $('<div id="fixed-element-' + element_id + '" class="sortable-elements" />');
26
+ $fixed_elements.append($tab);
27
+ $fixed_elements.tabs().tabs('refresh');
28
+ $fixed_elements.tabs('option', 'active', $('#fixed-elements > div').index($tab));
29
+ },
30
+
31
+ removeTab: function(element_id) {
32
+ var $fixed_elements = $('#fixed-elements');
33
+
34
+ $fixed_elements.find('a[href="#fixed-element-' + element_id + '"]').parent().remove();
35
+ $fixed_elements.find('div#fixed-element-' + element_id).remove();
36
+ $fixed_elements.tabs().tabs('refresh');
37
+ }
38
+ };
@@ -1,5 +1,3 @@
1
- #= require date-formatter
2
-
3
1
  window.Alchemy = {} if typeof(window.Alchemy) is 'undefined'
4
2
 
5
3
  # The admin sitemap Alchemy module
@@ -8,7 +6,7 @@ Alchemy.Sitemap =
8
6
  # Storing some objects.
9
7
  init: (options) ->
10
8
  @search_field = $(".search_input_field")
11
- @filter_field_clear = $('.js_filter_field_clear')
9
+ @filter_field_clear = $('.search_field_clear')
12
10
  @display = $('#page_filter_result')
13
11
  @sitemap_wrapper = $('#sitemap-wrapper p.loading')
14
12
  @template = Handlebars.compile($('#sitemap-template').html())
@@ -111,7 +109,7 @@ Alchemy.Sitemap =
111
109
  now = new Date()
112
110
  if $checkbox.is(':checked')
113
111
  $publication_date_fields.removeClass('hidden')
114
- $public_on_field.val Date.format(now, format)
112
+ $public_on_field[0]._flatpickr.setDate(now)
115
113
  else
116
114
  $publication_date_fields.addClass('hidden')
117
115
  $public_on_field.val('')
@@ -26,4 +26,4 @@ Alchemy.translations =
26
26
  datetime: "Y-m-d H:i"
27
27
  date: "Y-m-d"
28
28
  time: "H:i"
29
- start_of_week: 0
29
+ time_24hr: false
@@ -182,11 +182,12 @@
182
182
  cursor: zoom-in;
183
183
  }
184
184
 
185
- @mixin truncate($max-width, $display: inline-block) {
185
+ @mixin truncate($max-width, $display: inline-block, $wrap: normal) {
186
186
  display: $display;
187
187
  max-width: $max-width;
188
188
  overflow: hidden;
189
189
  text-overflow: ellipsis;
190
+ white-space: $wrap;
190
191
  }
191
192
 
192
193
  @mixin hint-hover-style {
@@ -76,6 +76,7 @@ $button-text-shadow: none !default;
76
76
  $button-box-shadow: 0px 1px 1px -1px #333 !default;
77
77
  $button-focus-box-shadow: 0px 1px 1px 0px $button-focus-border-color !default;
78
78
  $button-padding: 0.55em 2em !default;
79
+ $small-button-padding: 0.4em 1.25em !default;
79
80
  $button-margin: $form-field-margin !default;
80
81
 
81
82
  $secondary-button-bg-color: transparent !default;
@@ -112,12 +113,13 @@ $sitemap-highlight-color: rgba(#fffba5, 0.5) !default;
112
113
 
113
114
  $main-menu-width: 150px !default;
114
115
  $collapsed-main-menu-width: 48px !default;
116
+ $collapsed-main-menu-entry-max-width: 300px !default;
115
117
  $main-menu-bg-color: $dark-blue !default;
116
118
  $main-menu-active-bg-color: $dark-orange !default;
117
119
  $main-menu-active-text-color: $dark-blue !default;
118
120
  $main-menu-text-color: $white !default;
119
121
  $main-menu-icon-color: $white !default;
120
- $main-menu-entry-max-width: 100px !default;
122
+ $main-menu-entry-max-width: 110px !default;
121
123
  $toolbar-bg-color: $medium-gray !default;
122
124
  $toolbar-height: 46px !default;
123
125
  $element-toolbar-height: 37px !default;
@@ -135,7 +137,8 @@ $table-row-even-background-color: $white !default;
135
137
  $table-row-odd-background-color: rgba($white, 0.5) !default;
136
138
  $table-row-hover-color: rgba($light_yellow, 0.5) !default;
137
139
 
138
- $elements-window-width: 400px !default;
140
+ $elements-window-width: 22.5vw !default;
141
+ $elements-window-min-width: 400px !default;
139
142
  $element-header-bg-color: $medium-gray !default;
140
143
  $top-menu-height: 75px !default;
141
144
 
@@ -157,3 +160,5 @@ $select-hover-bg-color: $dark-blue !default;
157
160
  $select-hover-text-color: $white !default;
158
161
 
159
162
  $thumbnail-background-color: opacify($default-border-color, 1) !default;
163
+ $medium-screen-break-point: 700px;
164
+ $large-screen-break-point: 1000px;
@@ -19,7 +19,9 @@
19
19
  @import "alchemy/dashboard";
20
20
  @import "alchemy/elements";
21
21
  @import "alchemy/errors";
22
+ @import "alchemy/filter_field";
22
23
  @import "alchemy/flash";
24
+ @import "alchemy/flatpickr";
23
25
  @import "alchemy/fonts";
24
26
  @import "alchemy/forms";
25
27
  @import "alchemy/form_fields";
@@ -43,4 +45,3 @@
43
45
  @import "alchemy/upload";
44
46
  @import "alchemy/jquery-ui";
45
47
  @import "jquery.Jcrop.min";
46
- @import "jquery.datetimepicker";
@@ -1,3 +1,15 @@
1
+ .resources-header {
2
+ padding: 2*$default-padding;
3
+ }
4
+
5
+ .resources-table-wrapper {
6
+ padding-bottom: 60px;
7
+
8
+ &.with_tag_filter {
9
+ padding-right: 242px;
10
+ }
11
+ }
12
+
1
13
  div#image_assign_filter_and_image_sizing {
2
14
  width: 100%;
3
15
  height: 40px;
@@ -27,7 +39,6 @@ div#image_assign_filter_and_image_sizing {
27
39
  .picture_thumbnail {
28
40
  margin: 2*$default-margin;
29
41
  background-color: #fff;
30
- display: inline-block;
31
42
  position: relative;
32
43
  box-shadow: 0 0 0 1px $default-border-color;
33
44
  width: 160px;
@@ -77,10 +88,13 @@ div#image_assign_filter_and_image_sizing {
77
88
  }
78
89
  }
79
90
 
91
+ #pictures,
92
+ #overlay_picture_list {
93
+ display: flex;
94
+ flex-wrap: wrap;
95
+ }
96
+
80
97
  #pictures {
81
- margin-right: 232px;
82
- padding-bottom: 60px;
83
- overflow: hidden;
84
98
 
85
99
  .thumbnail_background {
86
100
  @include zoom-in;
@@ -21,7 +21,7 @@ button, input[type="submit"], a.button, input.button {
21
21
  }
22
22
 
23
23
  &.small {
24
- padding: $default-padding 3*$default-padding;
24
+ padding: $small-button-padding;
25
25
  vertical-align: inherit;
26
26
  line-height: 4*$default-padding;
27
27
  font-size: inherit;
@@ -59,7 +59,7 @@ $dialog-transition-duration: 150ms;
59
59
  .alchemy-dialog,
60
60
  .alchemy-image-overlay-dialog {
61
61
  position: relative;
62
- max-width: 100%;
62
+ max-width: calc(100vw - 16px);
63
63
  display: inline-block;
64
64
  vertical-align: middle;
65
65
  text-align: left;
@@ -3,26 +3,36 @@
3
3
  right: 0;
4
4
  top: $top-menu-height;
5
5
  z-index: 20;
6
- width: $elements-window-width;
6
+ width: calc(100vw - #{$collapsed-main-menu-width});
7
7
  height: calc(100vh - #{$top-menu-height});
8
8
  border-left: $default-border;
9
9
  background-color: $light-gray;
10
10
  transition: $transition-duration ease-in-out;
11
- transform: translate3d($elements-window-width - $default-border-width, 0, 0);
11
+ transform: translate3d(100%, 0, 0);
12
12
 
13
13
  .elements-window-visible & {
14
14
  transform: translate3d(0, 0, 0);
15
15
  }
16
+
17
+ // Fix for Tinymce fullscreen window positioning issues (GH#1511)
18
+ .mce-fullscreen & {
19
+ width: calc(100vw - #{$collapsed-main-menu-width - $default-border-width});
20
+ }
21
+
22
+ @media screen and (min-width: $large-screen-break-point) {
23
+ width: $elements-window-width;
24
+ min-width: $elements-window-min-width;
25
+ }
16
26
  }
17
27
 
18
28
  #element_area {
19
29
  height: calc(100vh - #{$top-menu-height + $toolbar-height});
20
30
  overflow-x: hidden;
21
31
  overflow-y: auto;
32
+ -webkit-overflow-scrolling: touch;
22
33
 
23
- .sortable_cell {
34
+ .sortable-elements {
24
35
  min-height: 100px;
25
- padding: 2*$default-padding $default-padding 2px;
26
36
  }
27
37
 
28
38
  textarea {
@@ -35,6 +45,11 @@
35
45
  }
36
46
  }
37
47
 
48
+ #main-content-elements,
49
+ .element-editor.is-fixed .nestable-elements {
50
+ padding: 2*$default-padding $default-padding 2px;
51
+ }
52
+
38
53
  .element-title {
39
54
  overflow: hidden;
40
55
  white-space: nowrap;
@@ -99,40 +114,6 @@
99
114
  }
100
115
  }
101
116
 
102
- .add_picture {
103
- float: left;
104
- margin: 1px;
105
- width: 119px;
106
- border: 1px solid #c0c0c0;
107
- border-radius: $default-border-radius;
108
- height: 123px;
109
-
110
- a {
111
- display: block;
112
- height: 100%;
113
- width: 100%;
114
- position: relative;
115
- text-decoration: none;
116
- overflow: hidden;
117
- text-align: center;
118
- line-height: 104px;
119
- border-radius: $default-border-radius;
120
- background-color: $light-gray;
121
-
122
- &:hover {
123
- background-color: $medium-gray;
124
- }
125
-
126
- .icon {
127
- font-size: 1.5em;
128
- position: absolute;
129
- top: 50%;
130
- left: 50%;
131
- transform: translate(-50%, -50%);
132
- }
133
- }
134
- }
135
-
136
117
  .element-editor {
137
118
  border: 1px solid $default-border-color;
138
119
  border-radius: $default-border-radius;
@@ -140,6 +121,11 @@
140
121
  margin-bottom: 2*$default-margin;
141
122
  transition: box-shadow $transition-duration;
142
123
 
124
+ &.is-fixed {
125
+ border-width: 0;
126
+ border-radius: 0;
127
+ }
128
+
143
129
  &.not-draggable {
144
130
  opacity: 0.5;
145
131
  }
@@ -152,7 +138,7 @@
152
138
  }
153
139
  }
154
140
 
155
- &.selected {
141
+ &.selected:not(.is-fixed) {
156
142
  border-color: #c3c3c3;
157
143
  box-shadow: 0 2px 8px rgba(#9b9b9b, 0.75);
158
144
  }
@@ -166,9 +152,12 @@
166
152
 
167
153
  &.dragged {
168
154
  border-style: dotted;
169
- height: 36px;
155
+ overflow: hidden;
170
156
 
171
- * { display: none }
157
+ &:not(.compact) {
158
+ height: 36px !important;
159
+ transition: height 0.2s;
160
+ }
172
161
  }
173
162
 
174
163
  &.with-contents, &.without-contents.not-nestable {
@@ -273,7 +262,6 @@
273
262
  .element-toolbar {
274
263
  padding: $default-padding 0;
275
264
  height: $element-toolbar-height;
276
- // background-color: #f0f0f0;
277
265
 
278
266
  .element_tools {
279
267
  float: left;
@@ -297,23 +285,6 @@
297
285
  flex-wrap: wrap;
298
286
  }
299
287
 
300
- .picture_gallery_images {
301
- overflow: hidden;
302
- margin: $default-margin 0;
303
- border: 1px solid $default-border-color;
304
- border-radius: $default-border-radius;
305
- background-color: $medium-gray;
306
- padding: 1px;
307
-
308
- .essence_picture {
309
- margin: 1px;
310
- float: left;
311
- height: 148px;
312
-
313
- .picture_thumbnail { margin: 0 }
314
- }
315
- }
316
-
317
288
  .picture_thumbnail .picture_image {
318
289
  overflow: hidden;
319
290
 
@@ -322,7 +293,7 @@
322
293
  }
323
294
  }
324
295
 
325
- #cells {
296
+ #fixed-elements {
326
297
  min-height: 100px;
327
298
  }
328
299
 
@@ -432,6 +403,7 @@
432
403
  }
433
404
 
434
405
  .picture_thumbnail {
406
+ display: inline-block;
435
407
  width: 160px;
436
408
  margin: $default-margin 0;
437
409
  padding-bottom: 28px;
@@ -462,25 +434,6 @@
462
434
  }
463
435
  }
464
436
 
465
- .draggable_picture {
466
- float: left;
467
-
468
- .picture_handle {
469
- cursor: move;
470
- }
471
- }
472
-
473
- .picture_thumbnail .picture_handle {
474
- position: absolute;
475
- z-index: 1;
476
- width: 100%;
477
- height: 97px;
478
- top: 0;
479
- left: 0;
480
- background-color: transparent;
481
- @extend .disable-user-select;
482
- }
483
-
484
437
  .content_editor.essence_file {
485
438
 
486
439
  .file {
@@ -598,8 +551,8 @@ select.long {
598
551
  }
599
552
 
600
553
  label {
601
- display: inline-block;
602
- margin-bottom: 2px;
554
+ display: block;
555
+ margin: $default-margin 0;
603
556
  font-size: $small-font-size;
604
557
  line-height: 15px;
605
558
  text-indent: 1px;
@@ -619,7 +572,7 @@ select.long {
619
572
 
620
573
  &.essence_select {
621
574
 
622
- label { margin-bottom: 4px }
575
+ label { margin-bottom: 2*$default-margin }
623
576
 
624
577
  .select2-container {
625
578
  width: 100%;
@@ -731,31 +684,142 @@ textarea.has_tinymce {
731
684
  top: -1px;
732
685
  }
733
686
 
734
- .nestable-elements {
687
+ .not-fixed .nestable-elements {
735
688
  box-shadow: inset 0 4px 8px -2px darken($medium-gray, 15%);
736
689
  background-color: $medium-gray;
737
690
 
738
691
  .expanded.element-editor > & {
739
- padding: 16px 8px 8px;
692
+ padding: 8px 4px 4px;
693
+ }
694
+
695
+ .add-nestable-element-button {
696
+ width: calc(50% - 8px);
697
+ margin: 4px;
698
+ text-align: center;
699
+ }
700
+ }
701
+
702
+ .is-fixed {
703
+ &.with-contents {
704
+ > .element-footer {
705
+ border-top: 0;
706
+ border-bottom: 1px solid $medium-gray;
707
+ }
708
+ }
709
+
710
+ > .nestable-elements .add-nestable-element-button {
711
+ width: 100%;
712
+ text-align: center;
740
713
  }
741
714
  }
742
715
 
743
- .nested-elements {
716
+ .not-fixed .nested-elements {
717
+ display: flex;
718
+ flex-wrap: wrap;
719
+
720
+ .element-editor,
721
+ .droppable_element_placeholder {
722
+ width: calc(100% - 8px);
723
+ margin: 4px;
724
+
725
+ &.compact {
726
+ width: calc(50% - 8px);
727
+ }
728
+ }
729
+
730
+ .element-editor {
731
+ position: relative;
732
+
733
+ &.compact {
734
+ .element-toolbar {
735
+ visibility: hidden;
736
+ position: absolute;
737
+ height: 35px;
738
+ padding: 2px 0;
739
+ opacity: 0;
740
+ z-index: 1;
741
+ border-bottom: $default-border;
742
+ background-color: $light-gray;
743
+ transition: all $transition-duration;
744
+ }
745
+
746
+ .element-header:hover + .element-toolbar,
747
+ .element-toolbar:hover {
748
+ visibility: visible;
749
+ opacity: 1;
750
+ }
751
+
752
+ .element-footer {
753
+ margin-top: 0;
754
+ padding-top: 0;
755
+ border-top: 0;
756
+
757
+ .button {
758
+ padding: $small-button-padding;
759
+ }
760
+ }
761
+
762
+ .element-title {
763
+ max-width: 75%;
764
+ }
765
+
766
+ &:not(.folded) .ajax-folder {
767
+ pointer-events: none;
768
+
769
+ i:before {
770
+ content: fa-content($fa-var-ellipsis-v);
771
+ }
772
+ }
773
+
774
+ .element_tools {
775
+ display: flex;
776
+ width: 100%;
777
+ justify-content: space-between;
778
+ margin-left: 0;
779
+ }
780
+
781
+ .element-content {
782
+ padding: 4px 8px;
783
+ }
784
+
785
+ .button_with_label {
786
+ margin: 0 4px;
787
+ }
788
+
789
+ .content_editor,
790
+ .picture_thumbnail {
791
+ width: 100%;
792
+ }
793
+
794
+ .picture_thumbnail {
795
+ margin: 0;
796
+ }
797
+
798
+ .thumbnail_background {
799
+ height: 115px;
800
+ }
801
+
802
+ textarea,
803
+ input[type="url"],
804
+ input[type="text"],
805
+ input[type="email"],
806
+ input[type="password"] {
807
+ padding: 0.5em;
808
+ height: auto;
809
+ }
810
+ }
811
+ }
744
812
 
745
813
  .element-header {
746
814
  background-color: transparent;
747
815
  }
748
816
 
749
817
  .element-toolbar {
750
- background-color: transparent;
818
+ width: 100%;
751
819
  border-top: 1px solid $medium-gray;
752
820
  }
753
821
  }
754
822
 
755
- .add-nestable-element-button {
756
- margin-top: 0;
757
- }
758
-
759
823
  .essence_date--label {
760
824
  position: absolute;
761
825
  right: 7px;