diff -u b/core/lib/Drupal/Core/Render/Element/Dropbutton.php b/core/lib/Drupal/Core/Render/Element/Dropbutton.php --- b/core/lib/Drupal/Core/Render/Element/Dropbutton.php +++ b/core/lib/Drupal/Core/Render/Element/Dropbutton.php @@ -35,7 +35,7 @@ public static function preRenderDropbutton($element) { $element['#attached']['library'][] = 'core/drupal.dropbutton'; $element['#attributes']['class'][] = 'dropbutton__menu'; - $element['#attributes']['class'][] = 'js-dropbutton__menu'; + $element['#attributes']['data-drupal-dropbutton-menu'] = TRUE; if (!isset($element['#theme_wrappers'])) { $element['#theme_wrappers'] = array(); } diff -u b/core/misc/dropbutton/dropbutton.js b/core/misc/dropbutton/dropbutton.js --- b/core/misc/dropbutton/dropbutton.js +++ b/core/misc/dropbutton/dropbutton.js @@ -8,13 +8,16 @@ "use strict"; /** - * Process elements with the .js-dropbutton class on page load. + * Process elements with the data-drupal-dropbutton attribute on page load. * * @type {Drupal~behavior} + * + * @prop {Drupal~behaviorAttach} attach + * Process elements with `data-drupal-dropbutton` attributes. */ Drupal.behaviors.dropButton = { attach: function (context, settings) { - var $dropbuttons = $(context).find('.js-dropbutton').once('dropbutton'); + var $dropbuttons = $(context).find('[data-drupal-dropbutton]').once('dropbutton'); if ($dropbuttons.length) { // Adds the delegated handler that will toggle dropdowns on click. var $body = $('body').once('dropbutton-click'); @@ -36,10 +39,11 @@ * @function Drupal.DropButton~dropbuttonClickHandler * * @param {jQuery.Event} e + * jQuery event object. */ function dropbuttonClickHandler(e) { e.preventDefault(); - $(e.target).closest('.js-dropbutton').toggleClass('is-open'); + $(e.target).closest('[data-drupal-dropbutton]').toggleClass('is-open'); } /** @@ -141,6 +145,7 @@ * Extend the DropButton constructor. */ $.extend(DropButton, /** @lends Drupal.DropButton */{ + /** * Store all processed DropButtons. * @@ -162,9 +167,8 @@ * passing false. */ toggle: function (show) { - var isBool = typeof show === 'boolean'; - show = isBool ? show : !this.$dropbutton.hasClass('is-open'); - this.$dropbutton.toggleClass('is-open', show); + var toggle = typeof show === 'boolean' ? show : !this.$dropbutton.hasClass('is-open'); + this.$dropbutton.toggleClass('is-open', toggle); }, /** @@ -201,6 +205,7 @@ /** * @param {jQuery.Event} e + * jQuery event object. */ focusOut: function (e) { this.hoverOut.call(this, e); @@ -208,28 +213,25 @@ /** * @param {jQuery.Event} e + * jQuery event object. */ focusIn: function (e) { this.hoverIn.call(this, e); } }); - $.extend(Drupal.theme, /** @lends Drupal.theme */{ - - /** - * A toggle is an interactive element often bound to a click handler. - * - * @param {object} options - * @param {string} [options.title] - * The HTML anchor title attribute and text for the inner span element. - * - * @return {string} - * A string representing a DOM fragment. - */ - dropbuttonToggle: function (options) { - return ''; - } - }); + /** + * A toggle is an interactive element often bound to a click handler. + * + * @param {string} title + * The text of the inner span element for screen readers. + * + * @return {string} + * A string representing a DOM fragment. + */ + Drupal.theme.dropbuttonToggle = function (title) { + return ''; + }; // Expose constructor in the public space. Drupal.DropButton = DropButton; diff -u b/core/modules/book/src/Tests/BookTest.php b/core/modules/book/src/Tests/BookTest.php --- b/core/modules/book/src/Tests/BookTest.php +++ b/core/modules/book/src/Tests/BookTest.php @@ -641,7 +641,7 @@ $this->drupalGet('admin/structure/book/' . $this->book->id()); $this->assertText($this->book->label(), 'The book title is displayed on the administrative book listing page.'); - $elements = $this->xpath('//table//div[@class="js-dropbutton"]//a'); + $elements = $this->xpath('//table//[@data-drupal-dropbutton]/ul/li/a'); $this->assertEqual((string) $elements[0], 'View', 'View link is found from the list.'); } diff -u b/core/modules/content_translation/src/Tests/ContentTranslationUITestBase.php b/core/modules/content_translation/src/Tests/ContentTranslationUITestBase.php --- b/core/modules/content_translation/src/Tests/ContentTranslationUITestBase.php +++ b/core/modules/content_translation/src/Tests/ContentTranslationUITestBase.php @@ -216,7 +216,7 @@ $elements = $this->xpath('//table//a[@href=:href]', array(':href' => $view_path)); $this->assertEqual((string) $elements[0], $entity->getTranslation($langcode)->label(), format_string('Label correctly shown for %language translation.', array('%language' => $langcode))); $edit_path = $entity->url('edit-form', array('language' => $language)); - $elements = $this->xpath('//table//div[@class="js-dropbutton"]//a[@href=:href]', array(':href' => $edit_path)); + $elements = $this->xpath('//table//[@data-drupal-dropbutton]/ul/li/a[@href=:href]', array(':href' => $edit_path)); $this->assertEqual((string) $elements[0], t('Edit'), format_string('Edit link correct for %language translation.', array('%language' => $langcode))); } } diff -u b/core/modules/field_ui/src/Tests/ManageFieldsTest.php b/core/modules/field_ui/src/Tests/ManageFieldsTest.php --- b/core/modules/field_ui/src/Tests/ManageFieldsTest.php +++ b/core/modules/field_ui/src/Tests/ManageFieldsTest.php @@ -154,7 +154,7 @@ // Assert entity operations for all fields. $number_of_links = 3; $number_of_links_found = 0; - $operation_links = $this->xpath('//div[@class = "js-dropbutton"]//a'); + $operation_links = $this->xpath('//div[@data-drupal-dropbutton]//a'); $url = base_path() . "admin/structure/types/manage/$type/fields/node.$type.body"; foreach ($operation_links as $link) { diff -u b/core/modules/language/config/optional/tour.tour.language.yml b/core/modules/language/config/optional/tour.tour.language.yml --- b/core/modules/language/config/optional/tour.tour.language.yml +++ b/core/modules/language/config/optional/tour.tour.language.yml @@ -44,7 +44,7 @@ body: '
Operations are provided for editing and deleting your languages.
You can edit the name and the direction of the language.
Deleted languages can be added back at a later time. Deleting a language will remove all interface translations associated with it, and content in this language will be set to be language neutral. Note that you cannot delete the default language of the site.
' weight: 5 attributes: - data-class: js-dropbutton + data-class: dropbutton-widget[data-drupal-dropbutton] language-continue: id: language-continue plugin: text diff -u b/core/modules/node/src/Tests/AssertButtonsTrait.php b/core/modules/node/src/Tests/AssertButtonsTrait.php --- b/core/modules/node/src/Tests/AssertButtonsTrait.php +++ b/core/modules/node/src/Tests/AssertButtonsTrait.php @@ -35,7 +35,7 @@ $this->assertTrue(empty($save_button)); // Dropbutton elements. - $elements = $this->xpath('//div[@class="js-dropbutton"]//input[@type="submit"]'); + $elements = $this->xpath('//div[@data-drupal-dropbutton]//input[@type="submit"]'); $this->assertEqual($count, count($elements)); foreach ($elements as $element) { $value = isset($element['value']) ? (string) $element['value'] : ''; @@ -46,7 +46,7 @@ else { // Assert there is a save button. $this->assertTrue(!empty($save_button)); - $this->assertNoRaw('js-dropbutton'); + $this->assertNoRaw('data-drupal-dropbutton'); } } } diff -u b/core/modules/system/templates/dropbutton-wrapper.html.twig b/core/modules/system/templates/dropbutton-wrapper.html.twig --- b/core/modules/system/templates/dropbutton-wrapper.html.twig +++ b/core/modules/system/templates/dropbutton-wrapper.html.twig @@ -14,7 +14,7 @@ #} {% if children %} {% spaceless %} -