blacklight-spotlight 4.1.2 → 4.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (107) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +3 -3
  3. data/app/assets/javascripts/spotlight/spotlight.esm.js +146 -27
  4. data/app/assets/javascripts/spotlight/spotlight.esm.js.map +1 -1
  5. data/app/assets/javascripts/spotlight/spotlight.js +146 -27
  6. data/app/assets/javascripts/spotlight/spotlight.js.map +1 -1
  7. data/app/assets/stylesheets/spotlight/_blacklight_configuration.scss +19 -1
  8. data/app/components/spotlight/breadcrumbs_component.html.erb +19 -0
  9. data/app/components/spotlight/breadcrumbs_component.rb +23 -0
  10. data/app/components/spotlight/exhibit_navbar_component.html.erb +25 -0
  11. data/app/components/spotlight/exhibit_navbar_component.rb +12 -0
  12. data/app/components/spotlight/tag_list_form_component.html.erb +14 -0
  13. data/app/components/spotlight/tag_list_form_component.rb +13 -0
  14. data/app/controllers/concerns/spotlight/controller.rb +9 -1
  15. data/app/controllers/concerns/spotlight/search_helper.rb +2 -2
  16. data/app/controllers/spotlight/about_pages_controller.rb +1 -1
  17. data/app/controllers/spotlight/admin_users_controller.rb +2 -2
  18. data/app/controllers/spotlight/appearances_controller.rb +4 -4
  19. data/app/controllers/spotlight/browse_controller.rb +2 -2
  20. data/app/controllers/spotlight/bulk_actions_controller.rb +1 -1
  21. data/app/controllers/spotlight/bulk_updates_controller.rb +7 -2
  22. data/app/controllers/spotlight/catalog_controller.rb +11 -10
  23. data/app/controllers/spotlight/contacts_controller.rb +5 -5
  24. data/app/controllers/spotlight/custom_fields_controller.rb +5 -5
  25. data/app/controllers/spotlight/custom_search_fields_controller.rb +5 -5
  26. data/app/controllers/spotlight/dashboards_controller.rb +4 -4
  27. data/app/controllers/spotlight/exhibits_controller.rb +6 -5
  28. data/app/controllers/spotlight/feature_pages_controller.rb +5 -5
  29. data/app/controllers/spotlight/featured_images_controller.rb +1 -1
  30. data/app/controllers/spotlight/groups_controller.rb +1 -1
  31. data/app/controllers/spotlight/home_pages_controller.rb +2 -2
  32. data/app/controllers/spotlight/job_trackers_controller.rb +3 -3
  33. data/app/controllers/spotlight/metadata_configurations_controller.rb +3 -3
  34. data/app/controllers/spotlight/pages_controller.rb +3 -3
  35. data/app/controllers/spotlight/resources/csv_upload_controller.rb +1 -1
  36. data/app/controllers/spotlight/resources_controller.rb +4 -4
  37. data/app/controllers/spotlight/roles_controller.rb +4 -4
  38. data/app/controllers/spotlight/search_configurations_controller.rb +3 -3
  39. data/app/controllers/spotlight/searches_controller.rb +5 -5
  40. data/app/controllers/spotlight/sites_controller.rb +4 -4
  41. data/app/controllers/spotlight/tags_controller.rb +3 -3
  42. data/app/controllers/spotlight/translations_controller.rb +5 -5
  43. data/app/helpers/spotlight/application_helper.rb +2 -2
  44. data/app/helpers/spotlight/crop_helper.rb +1 -1
  45. data/app/helpers/spotlight/pages_helper.rb +7 -0
  46. data/app/helpers/spotlight/title_helper.rb +2 -2
  47. data/app/javascript/spotlight/admin/blocks/browse_group_categories_block.js +1 -1
  48. data/app/javascript/spotlight/admin/blocks/resources_block.js +82 -1
  49. data/app/javascript/spotlight/admin/blocks/solr_documents_embed_block.js +1 -1
  50. data/app/javascript/spotlight/admin/blocks/uploaded_items_block.js +21 -0
  51. data/app/javascript/spotlight/admin/edit_in_place.js +27 -0
  52. data/app/javascript/spotlight/admin/index.js +0 -2
  53. data/app/javascript/spotlight/admin/sir-trevor/locales.js +11 -0
  54. data/app/jobs/concerns/spotlight/job_tracking.rb +1 -1
  55. data/app/jobs/spotlight/add_tags_job.rb +2 -2
  56. data/app/jobs/spotlight/add_uploads_from_csv.rb +1 -1
  57. data/app/jobs/spotlight/change_visibility_job.rb +2 -2
  58. data/app/jobs/spotlight/process_bulk_updates_csv_job.rb +2 -2
  59. data/app/jobs/spotlight/reindex_exhibit_job.rb +1 -1
  60. data/app/jobs/spotlight/reindex_job.rb +6 -6
  61. data/app/jobs/spotlight/remove_tags_job.rb +2 -2
  62. data/app/jobs/spotlight/rename_tags_job.rb +2 -2
  63. data/app/models/breadcrumb.rb +15 -0
  64. data/app/models/concerns/spotlight/exhibit_defaults.rb +1 -1
  65. data/app/models/concerns/spotlight/exhibit_documents.rb +2 -2
  66. data/app/models/concerns/spotlight/solr_document/finder.rb +4 -4
  67. data/app/models/concerns/spotlight/solr_document.rb +4 -4
  68. data/app/models/concerns/spotlight/translatables.rb +1 -1
  69. data/app/models/spotlight/analytics/ga.rb +3 -3
  70. data/app/models/spotlight/attachment.rb +1 -1
  71. data/app/models/spotlight/background_job_progress.rb +1 -1
  72. data/app/models/spotlight/contact_email.rb +1 -1
  73. data/app/models/spotlight/contact_form.rb +2 -2
  74. data/app/models/spotlight/custom_field.rb +2 -2
  75. data/app/models/spotlight/custom_search_field.rb +2 -2
  76. data/app/models/spotlight/job_tracker.rb +1 -1
  77. data/app/models/spotlight/page.rb +2 -2
  78. data/app/models/spotlight/resources/iiif_service.rb +4 -4
  79. data/app/models/spotlight/role.rb +1 -1
  80. data/app/models/spotlight/search.rb +2 -2
  81. data/app/services/spotlight/bulk_updates_csv_template_service.rb +2 -2
  82. data/app/services/spotlight/clone_translated_page_from_locale.rb +1 -1
  83. data/app/services/spotlight/etl/pipeline.rb +1 -1
  84. data/app/views/shared/_exhibit_navbar.html.erb +2 -24
  85. data/app/views/shared/_masthead.html.erb +1 -1
  86. data/app/views/spotlight/exhibits/_form.html.erb +1 -1
  87. data/app/views/spotlight/exhibits/_new_exhibit_form.html.erb +1 -1
  88. data/app/views/spotlight/metadata_configurations/_metadata_field.html.erb +16 -5
  89. data/app/views/spotlight/metadata_configurations/edit.html.erb +2 -2
  90. data/app/views/spotlight/sir_trevor/blocks/_solr_documents_block.html.erb +3 -3
  91. data/app/views/spotlight/sir_trevor/blocks/_solr_documents_carousel_block.html.erb +3 -3
  92. data/app/views/spotlight/sir_trevor/blocks/_solr_documents_features_block.html.erb +3 -3
  93. data/app/views/spotlight/sir_trevor/blocks/_solr_documents_grid_block.html.erb +3 -3
  94. data/app/views/spotlight/sir_trevor/blocks/_uploaded_items_block.html.erb +3 -2
  95. data/config/locales/spotlight.en.yml +4 -0
  96. data/lib/generators/spotlight/templates/catalog_controller.rb +1 -0
  97. data/lib/generators/spotlight/templates/config/initializers/spotlight_initializer.rb +4 -0
  98. data/lib/migration/iiif.rb +3 -3
  99. data/lib/spotlight/engine.rb +6 -26
  100. data/lib/spotlight/version.rb +1 -1
  101. data/lib/tasks/spotlight_tasks.rake +3 -3
  102. data/spec/factories/exhibits.rb +1 -1
  103. data/spec/support/views/test_view_helpers.rb +0 -1
  104. metadata +11 -27
  105. data/app/builders/spotlight/bootstrap_breadcrumbs_builder.rb +0 -39
  106. data/app/javascript/spotlight/admin/appearance.js +0 -22
  107. data/app/views/shared/_breadcrumbs.html.erb +0 -7
@@ -4056,29 +4056,6 @@
4056
4056
  }
4057
4057
  }
4058
4058
 
4059
- class Appearance {
4060
- connect(){
4061
- $("[data-behavior='restore-default']").each(function(){
4062
- var hidden = $("[data-default-value]", $(this));
4063
- var value = $($("[data-in-place-edit-target]", $(this)).data('in-place-edit-target'), $(this));
4064
- var button = $("[data-restore-default]", $(this));
4065
- hidden.on('blur', function(){
4066
- if( $(this).val() == $(this).data('default-value') ) {
4067
- button.addClass('d-none');
4068
- } else {
4069
- button.removeClass('d-none');
4070
- }
4071
- });
4072
- button.on('click', function(e){
4073
- e.preventDefault();
4074
- hidden.val(hidden.data('default-value'));
4075
- value.text(hidden.data('default-value'));
4076
- button.hide();
4077
- });
4078
- });
4079
- }
4080
- }
4081
-
4082
4059
  class BlacklightConfiguration {
4083
4060
  connect() {
4084
4061
  // Add Select/Deselect all button behavior
@@ -4635,6 +4612,33 @@
4635
4612
  return false;
4636
4613
  });
4637
4614
  });
4615
+
4616
+ $("[data-behavior='restore-default']").each(function(){
4617
+ var hidden = $("[data-default-value]", $(this));
4618
+ var value = $($("[data-in-place-edit-target]", $(this)).data('in-place-edit-target'), $(this));
4619
+ var button = $("[data-restore-default]", $(this));
4620
+
4621
+ hidden.on('keypress', function(e) {
4622
+ if(e.which == 13) {
4623
+ hidden.trigger('blur');
4624
+ return false;
4625
+ }
4626
+ });
4627
+
4628
+ hidden.on('blur', function(){
4629
+ if( $(this).val() == $(this).data('default-value') ) {
4630
+ button.addClass('d-none');
4631
+ } else {
4632
+ button.removeClass('d-none');
4633
+ }
4634
+ });
4635
+ button.on('click', function(e){
4636
+ e.preventDefault();
4637
+ hidden.val(hidden.data('default-value'));
4638
+ value.text(hidden.data('default-value'));
4639
+ button.hide();
4640
+ });
4641
+ });
4638
4642
  }
4639
4643
  }
4640
4644
 
@@ -5137,6 +5141,7 @@
5137
5141
  };
5138
5142
 
5139
5143
  // Place all the behaviors and hooks related to the matching controller here.
5144
+ // All this logic will automatically be available in application.js.
5140
5145
 
5141
5146
  class Pages {
5142
5147
  connect(){
@@ -5603,6 +5608,8 @@
5603
5608
  }
5604
5609
 
5605
5610
  // Visibility toggle for items in an exhibit, based on Blacklight's bookmark toggle
5611
+ // See: https://github.com/projectblacklight/blacklight/blob/main/app/javascript/blacklight/bookmark_toggle.js
5612
+
5606
5613
 
5607
5614
  const VisibilityToggle = (e) => {
5608
5615
  if (e.target.matches('[data-checkboxsubmit-target="checkbox"]')) {
@@ -5929,10 +5936,24 @@
5929
5936
  formable: true,
5930
5937
  autocompleteable: true,
5931
5938
  show_heading: true,
5939
+ show_alt_text: true,
5932
5940
 
5933
5941
  title: function() { return i18n.t("blocks:" + this.type + ":title"); },
5934
5942
  description: function() { return i18n.t("blocks:" + this.type + ":description"); },
5935
-
5943
+ alt_text_guidelines: function() {
5944
+ if (this.show_alt_text) {
5945
+ return i18n.t("blocks:alt_text_guidelines:intro");
5946
+ }
5947
+ return "";
5948
+ },
5949
+ alt_text_guidelines_link: function() {
5950
+ if (this.show_alt_text) {
5951
+ var link_url = i18n.t("blocks:alt_text_guidelines:link_url");
5952
+ var link_label = i18n.t("blocks:alt_text_guidelines:link_label");
5953
+ return '<a target="_blank" href="' + link_url + '">' + link_label + '</a>';
5954
+ }
5955
+ return "";
5956
+ },
5936
5957
  icon_name: "resources",
5937
5958
  blockGroup: function() { return i18n.t("blocks:group:items") },
5938
5959
 
@@ -5942,6 +5963,8 @@
5942
5963
  show_secondary_field_key: "show-secondary-caption",
5943
5964
 
5944
5965
  display_checkbox: "display-checkbox",
5966
+ decorative_checkbox: "decorative-checkbox",
5967
+ alt_text_textarea: "alt-text-textarea",
5945
5968
 
5946
5969
  globalIndex: 0,
5947
5970
 
@@ -5949,6 +5972,13 @@
5949
5972
  return [];
5950
5973
  },
5951
5974
 
5975
+ _altTextFieldsHTML: function(index, data) {
5976
+ if (this.show_alt_text) {
5977
+ return this.altTextHTML(index, data);
5978
+ }
5979
+ return "";
5980
+ },
5981
+
5952
5982
  _itemPanel: function(data) {
5953
5983
  var index = "item_" + this.globalIndex++;
5954
5984
  var checked;
@@ -5979,6 +6009,7 @@
5979
6009
  <div class="main">
5980
6010
  <div class="title card-title">${data.title}</div>
5981
6011
  <div>${(data.slug || data.id)}</div>
6012
+ ${this._altTextFieldsHTML(index, data)}
5982
6013
  </div>
5983
6014
  <div class="remove float-right float-end">
5984
6015
  <a data-item-grid-panel-remove="true" href="#">${i18n.t("blocks:resources:panel:remove")}</a>
@@ -6015,6 +6046,7 @@
6015
6046
 
6016
6047
  createItemPanel: function(data) {
6017
6048
  var panel = this._itemPanel(data);
6049
+ this.attachAltTextHandlers(panel);
6018
6050
  $(panel).appendTo($('.panels > ol', this.inner));
6019
6051
  $('[data-behavior="nestable"]', this.inner).trigger('change');
6020
6052
  },
@@ -6047,11 +6079,67 @@
6047
6079
  return `<div class="form resources-admin clearfix">
6048
6080
  <div class="widget-header">
6049
6081
  ${this.description()}
6082
+ ${this.alt_text_guidelines()}
6083
+ ${this.alt_text_guidelines_link()}
6050
6084
  </div>
6051
6085
  ${this.content()}
6052
6086
  </div>`
6053
6087
  },
6054
6088
 
6089
+ _altTextData: function(data) {
6090
+ const isDecorative = data.decorative;
6091
+ const altText = isDecorative ? '' : (data.alt_text || '');
6092
+ const altTextBackup = data.alt_text_backup || '';
6093
+ const placeholderAttr = isDecorative ? '' : `placeholder="${i18n.t("blocks:resources:alt_text:placeholder")}"`;
6094
+ const disabledAttr = isDecorative ? 'disabled' : '';
6095
+
6096
+ return { isDecorative, altText, altTextBackup, placeholderAttr, disabledAttr };
6097
+ },
6098
+
6099
+ altTextHTML: function(index, data) {
6100
+ const { isDecorative, altText, altTextBackup, placeholderAttr, disabledAttr } = this._altTextData(data);
6101
+ return `<div class="mt-2 pt-2 d-flex">
6102
+ <div class="me-2 mr-2">
6103
+ <label class="col-form-label pb-0 pt-1" for="${this.formId(this.alt_text_textarea + '_' + data.id)}">${i18n.t("blocks:resources:alt_text:alternative_text")}</label>
6104
+ <div class="form-check mb-1 justify-content-end">
6105
+ <input class="form-check-input" type="checkbox"
6106
+ id="${this.formId(this.decorative_checkbox + '_' + data.id)}" name="item[${index}][decorative]" ${isDecorative ? 'checked' : ''}>
6107
+ <label class="form-check-label" for="${this.formId(this.decorative_checkbox + '_' + data.id)}">${i18n.t("blocks:resources:alt_text:decorative")}</label>
6108
+ </div>
6109
+ </div>
6110
+ <div class="flex-grow-1 flex-fill d-flex">
6111
+ <input type="hidden" name="item[${index}][alt_text_backup]" value="${altTextBackup}" />
6112
+ <textarea class="form-control w-100" rows="2" ${placeholderAttr}
6113
+ id="${this.formId(this.alt_text_textarea + '_' + data.id)}" name="item[${index}][alt_text]" ${disabledAttr}>${altText}</textarea>
6114
+ </div>
6115
+ </div>`
6116
+ },
6117
+
6118
+ attachAltTextHandlers: function(panel) {
6119
+ if (this.show_alt_text) {
6120
+ const decorativeCheckbox = $('input[name$="[decorative]"]', panel);
6121
+ const altTextInput = $('textarea[name$="[alt_text]"]', panel);
6122
+ const altTextBackupInput = $('input[name$="[alt_text_backup]"]', panel);
6123
+
6124
+ decorativeCheckbox.on('change', function() {
6125
+ const isDecorative = this.checked;
6126
+ if (isDecorative) {
6127
+ altTextBackupInput.val(altTextInput.val());
6128
+ altTextInput.val('');
6129
+ } else {
6130
+ altTextInput.val(altTextBackupInput.val());
6131
+ }
6132
+ altTextInput
6133
+ .prop('disabled', isDecorative)
6134
+ .attr('placeholder', isDecorative ? '' : i18n.t("blocks:resources:alt_text:placeholder"));
6135
+ });
6136
+
6137
+ altTextInput.on('input', function() {
6138
+ $(this).data('lastValue', $(this).val());
6139
+ });
6140
+ }
6141
+ },
6142
+
6055
6143
  onBlockRender: function() {
6056
6144
  Module.init($('[data-behavior="nestable"]', this.inner));
6057
6145
 
@@ -6241,7 +6329,7 @@
6241
6329
  },
6242
6330
 
6243
6331
  item_options: function() { return `
6244
- '<label>
6332
+ <label>
6245
6333
  <input type="hidden" name="display-item-counts" value="false" />
6246
6334
  <input type="checkbox" name="display-item-counts" value="true" checked />
6247
6335
  ${i18n.t("blocks:browse_group_categories:item_counts")}
@@ -6676,7 +6764,7 @@
6676
6764
 
6677
6765
  return SirTrevor.Blocks.SolrDocumentsBase.extend({
6678
6766
  type: "solr_documents_embed",
6679
-
6767
+ show_alt_text: false,
6680
6768
  icon_name: "item_embed",
6681
6769
 
6682
6770
  item_options: function() { return "" },
@@ -6840,6 +6928,7 @@
6840
6928
  <label for="${this.formId('link_' + dataId)}" class="col-form-label col-md-3">${i18n.t("blocks:uploaded_items:link")}</label>
6841
6929
  <input type="text" class="form-control col" id="${this.formId('link_' + dataId)}" name="item[${index}][link]" data-field="link"/>
6842
6930
  </div>
6931
+ ${this._altTextFieldsHTML(index, data)}
6843
6932
  </div>
6844
6933
  <div class="remove float-right float-end">
6845
6934
  <a data-item-grid-panel-remove="true" href="#">${i18n.t("blocks:resources:panel:remove")}</a>
@@ -6867,6 +6956,8 @@
6867
6956
  return `<div class="form oembed-text-admin clearfix">
6868
6957
  <div class="widget-header">
6869
6958
  ${this.description()}
6959
+ ${this.alt_text_guidelines()}
6960
+ ${this.alt_text_guidelines_link()}
6870
6961
  </div>
6871
6962
  <div class="row">
6872
6963
  <div class="form-group mb-3 col-md-8">
@@ -6886,6 +6977,24 @@
6886
6977
  </div>`
6887
6978
  },
6888
6979
 
6980
+ altTextHTML: function(index, data) {
6981
+ const { isDecorative, altText, altTextBackup, placeholderAttr, disabledAttr } = this._altTextData(data);
6982
+ return `
6983
+ <div class="field row mr-3 me-3">
6984
+ <div class="col-lg-3 ps-md-2 pl-md-2">
6985
+ <label class="col-form-label text-nowrap pb-0 pt-1 justify-content-md-start justify-content-lg-end d-flex" for="${this.formId(this.alt_text_textarea + '_' + data.id)}">${i18n.t("blocks:resources:alt_text:alternative_text")}</label>
6986
+ <div class="form-check d-flex justify-content-md-start justify-content-lg-end">
6987
+ <input class="form-check-input" type="checkbox"
6988
+ id="${this.formId(this.decorative_checkbox + '_' + data.id)}" name="item[${index}][decorative]" ${isDecorative ? 'checked' : ''}>
6989
+ <label class="form-check-label" for="${this.formId(this.decorative_checkbox + '_' + data.id)}">${i18n.t("blocks:resources:alt_text:decorative")}</label>
6990
+ </div>
6991
+ </div>
6992
+ <input type="hidden" name="item[${index}][alt_text_backup]" value="${altTextBackup}" />
6993
+ <textarea class="col-lg-9" rows="2" ${placeholderAttr}
6994
+ id="${this.formId(this.alt_text_textarea + '_' + data.id)}" name="item[${index}][alt_text]" ${disabledAttr}>${altText}</textarea>
6995
+ </div>`
6996
+ },
6997
+
6889
6998
  zpr_key: 'zpr_link'
6890
6999
  });
6891
7000
  })();
@@ -7096,6 +7205,11 @@
7096
7205
  drag: "Drag",
7097
7206
  display: "Display?",
7098
7207
  remove: "Remove"
7208
+ },
7209
+ alt_text: {
7210
+ decorative: "Decorative",
7211
+ alternative_text: "Alternative text",
7212
+ placeholder: "Enter alt text for this item..."
7099
7213
  }
7100
7214
  },
7101
7215
 
@@ -7161,6 +7275,12 @@
7161
7275
  group: {
7162
7276
  undefined: "Standard widgets",
7163
7277
  items: "Exhibit item widgets"
7278
+ },
7279
+
7280
+ alt_text_guidelines: {
7281
+ intro: 'For each item, please enter alternative text or appropriately check the decorative box. ',
7282
+ link_label: 'Guidelines for writing alt text.',
7283
+ link_url: 'https://www.w3.org/WAI/tutorials/images/'
7164
7284
  }
7165
7285
  });
7166
7286
 
@@ -7171,7 +7291,6 @@
7171
7291
  connect() {
7172
7292
  new AddAnother().connect();
7173
7293
  new AddNewButton().connect();
7174
- new Appearance().connect();
7175
7294
  new CopyEmailAddress().connect();
7176
7295
  new Croppable().connect();
7177
7296
  new EditInPlace().connect();