Last active
August 29, 2015 14:04
-
-
Save fabsor/27b8de2ce2b3785e6330 to your computer and use it in GitHub Desktop.
patch for refererences dialog edit
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
diff --git a/js/references-dialog.js b/js/references-dialog.js | |
index 0c23b31..23caa22 100644 | |
--- a/js/references-dialog.js | |
+++ b/js/references-dialog.js | |
@@ -1,52 +1,123 @@ | |
(function ($) { | |
- | |
var $window = $(window); | |
- | |
Drupal.behaviors.referencesDialog = { | |
- attach: function (context, settings) { | |
- // Add appropriate classes on all fields that should have it. This is | |
- // necessary since we don't actually know what markup we are dealing with. | |
- if (typeof settings.ReferencesDialog !== 'undefined') { | |
- $.each(settings.ReferencesDialog.fields, function (key, widget_settings) { | |
- $('.' + key + ' a.references-dialog-activate', context).click(function (e) { | |
- e.preventDefault(); | |
- Drupal.ReferencesDialog.open($(this).attr('href'), $(this).html()); | |
- Drupal.ReferencesDialog.entityIdReceived = function (entity_type, entity_id, label) { | |
- if (typeof widget_settings.format !== 'undefined') { | |
- var value = widget_settings.format | |
- .replace('$label', label) | |
- .replace('$entity_id', entity_id) | |
- .replace('$entity_type', entity_type); | |
- } | |
- // If we have a callback path, let's invoke that. | |
- if (typeof widget_settings.callback_path !== 'undefined') { | |
- var entity_info = { | |
- label: label, | |
- entity_id: entity_id, | |
- entity_type: entity_type | |
- }; | |
- Drupal.ReferencesDialog.invokeCallback(widget_settings.callback_path, entity_info, widget_settings.callback_settings); | |
- } | |
- // If we have a target, use that. | |
- else if (typeof widget_settings.target !== 'undefined') { | |
- var target = $('#' + widget_settings.target); | |
- target.val(value); | |
- target.change(); | |
+ | |
+ /** | |
+ * Manage edit links by doing access checks and adding edit links | |
+ * where appropriate. | |
+ * @param field_name the name of the field | |
+ * @param target the target jQuery element. | |
+ * @param the settings for the widget handling the field. | |
+ */ | |
+ editLinkController: function (field_name, settings) { | |
+ var _this = this; | |
+ return function () { | |
+ var val = $(this).val(); | |
+ var result = val.match(settings.match) | |
+ if (result && result[1]) { | |
+ var entity_id = result[1]; | |
+ var url = '$callback/$entity_type/$entity_id' | |
+ .replace('$callback', _this.settings.access_callback) | |
+ .replace('$entity_type', settings.entity_type) | |
+ .replace('$entity_id', entity_id) | |
+ $.get(url, function (data) { | |
+ if (data.access) { | |
+ var selector = '.dialog-links.' + field_name + ' > ul'; | |
+ if ($(selector + ' .edit-dialog').size() === 0) { | |
+ $(selector) | |
+ .append('<li><a href="' + data.path + | |
+ '" class="edit-dialog references-dialog-activate">' + | |
+ Drupal.t('Edit') + '</a></li>'); | |
+ $(selector + ' .edit-dialog').click(_this.dialogController(field_name, settings)); | |
} | |
- // If we have none of the above, we just insert the value in the item | |
- // that invoked this. | |
else { | |
- var key_el = $('#' + key); | |
- key_el.val(value); | |
- key_el.change(); | |
+ $(selector + ' .edit-dialog').attr('href', data.path); | |
} | |
} | |
- return false; | |
}); | |
- }); | |
+ } | |
+ }; | |
+ }, | |
+ | |
+ /** | |
+ * Get the target jQuery element. This will not work if the | |
+ * widget settings are fetched from a callback. | |
+ * @return | |
+ * The jquery element of the target, or null if the target | |
+ * is fetched with a callback. | |
+ */ | |
+ getTarget: function (field_name, settings) { | |
+ if (settings.target) { | |
+ return $('#' + widget_settings.target); | |
} | |
+ else if (!settings.callback_path){ | |
+ return $('#' + field_name); | |
+ } | |
+ }, | |
+ | |
+ /** | |
+ * Manage opening and return values from dialogs. | |
+ * @param field_name the name of the field | |
+ * param settings settings for the widget. | |
+ * @return a function that can be used in an event. | |
+ */ | |
+ dialogController: function (field_name, settings) { | |
+ var _this = this; | |
+ return function (e) { | |
+ e.preventDefault(); | |
+ Drupal.ReferencesDialog.open($(this).attr('href'), $(this).html()); | |
+ Drupal.ReferencesDialog.entityIdReceived = function (entity_type, entity_id, label) { | |
+ if (settings.format) { | |
+ var value = settings.format | |
+ .replace('$label', label) | |
+ .replace('$entity_id', entity_id) | |
+ .replace('$entity_type', entity_type); | |
+ } | |
+ var target = _this.getTarget(field_name, settings); | |
+ if (target) { | |
+ target.val(value); | |
+ target.change(); | |
+ } | |
+ // We can't get the target in the cases where | |
+ // we have a custom callback. | |
+ else { | |
+ var entity_info = { | |
+ label: label, | |
+ entity_id: entity_id, | |
+ entity_type: entity_type | |
+ }; | |
+ Drupal.ReferencesDialog | |
+ .invokeCallback(settings.callback_path, entity_info, | |
+ settings.callback_settings); | |
+ } | |
+ } | |
+ return false; | |
+ }; | |
+ }, | |
+ attach: function (context, settings) { | |
+ if (typeof settings.ReferencesDialog === 'undefined') { | |
+ return; | |
+ } | |
+ var _this = this; | |
+ this.settings = settings.ReferencesDialog; | |
+ this.context = context; | |
+ // Add appropriate classes on all fields that should have it. This is | |
+ // necessary since we don't actually know what markup we are dealing with. | |
+ $.each(this.settings.fields, function (key, widget_settings) { | |
+ var target = _this.getTarget(key, widget_settings); | |
+ // We can insert an edit link automatically if the widget provider | |
+ // supplied us with a match regexp and an entity type. | |
+ if (target && widget_settings.editable && widget_settings.match | |
+ && widget_settings.entity_type) { | |
+ var editController = _this.editLinkController(key, widget_settings); | |
+ target.change(editController); | |
+ target.blur(editController); | |
+ } | |
+ // Attach a dialog controller to our links. | |
+ $('.' + key + ' a.references-dialog-activate', context).click(_this.dialogController(key, widget_settings)); | |
+ }); | |
} | |
- }; | |
+ } | |
/** | |
* Our dialog object. Can be used to open a dialog to anywhere. | |
diff --git a/references_dialog.api.php b/references_dialog.api.php | |
index 73835c6..60a451d 100644 | |
--- a/references_dialog.api.php | |
+++ b/references_dialog.api.php | |
@@ -17,6 +17,9 @@ | |
* An array keyed by the widget you want to attach links to. This array | |
* should contain the following keys: | |
* - 'element_type': The type of FAPI element the widget is. | |
+ * - 'entity_type': The type of entity that is being created by this widget. | |
+ * - 'type_callback': Specify a callback if the entity may vary. | |
+ * - 'match': A regular expreession that matches the id from a textarea. | |
* - 'format': The format in which the data should be inserted as a value | |
* into the form element. The following patterns are provided, $label, $entity_id and $entity_type. | |
* - operations: An array of available operations. | |
diff --git a/references_dialog.dialog_widgets.inc b/references_dialog.dialog_widgets.inc | |
index 02efc48..a6d6888 100644 | |
--- a/references_dialog.dialog_widgets.inc | |
+++ b/references_dialog.dialog_widgets.inc | |
@@ -15,6 +15,7 @@ function references_dialog_references_dialog_widgets() { | |
'dialog_form' => 'node_reference_dialog_form', | |
'entity_type' => 'node', | |
'format' => '$label [nid: $entity_id]', | |
+ 'match' => 'nid:\s?([1-9][0-9]*)', | |
'views_query' => 'references_dialog_node_reference_views_query', | |
'operations' => array( | |
'search' => array( | |
@@ -35,6 +36,7 @@ function references_dialog_references_dialog_widgets() { | |
'element_type' => 'textfield', | |
'entity_type' => 'user', | |
'format' => '$label [uid: $entity_id]', | |
+ 'match' => 'uid:\s?([1-9][0-9]*)', | |
'operations' => array( | |
'search' => array( | |
'function' => 'references_dialog_get_field_search_links', | |
@@ -56,6 +58,7 @@ function references_dialog_references_dialog_widgets() { | |
'views_query' => 'references_dialog_entityreference_views_query', | |
'type_callback' => 'references_dialog_entityreference_get_type', | |
'format' => '$label ($entity_id)', | |
+ 'match' => '\(([1-9][0-9]*)\)', | |
'operations' => array( | |
'edit' => array( | |
'function' => 'references_dialog_entityreference_edit_link', | |
diff --git a/references_dialog.module b/references_dialog.module | |
index 26b203e..5973c75 100644 | |
--- a/references_dialog.module | |
+++ b/references_dialog.module | |
@@ -22,7 +22,17 @@ function references_dialog_element_info() { | |
*/ | |
function references_dialog_attached() { | |
return array( | |
- 'js' => array(drupal_get_path('module', 'references_dialog') . '/js/references-dialog.js'), | |
+ 'js' => array( | |
+ drupal_get_path('module', 'references_dialog') . '/js/references-dialog.js', | |
+ array( | |
+ 'data' => array( | |
+ 'ReferencesDialog' => array( | |
+ 'access_callback' => url('references-dialog/access'), | |
+ ), | |
+ ), | |
+ 'type' => 'setting', | |
+ ), | |
+ ), | |
'css' => array(drupal_get_path('module', 'references_dialog') . '/css/references-dialog-admin.css'), | |
'library' => array(array('system', 'ui.dialog')), | |
); | |
@@ -56,9 +66,25 @@ function references_dialog_menu() { | |
'access callback' => 'references_dialog_redirect_access', | |
'access arguments' => array(2, 3), | |
); | |
+ // Determine if we have access to create or update entities | |
+ // of a particular type. | |
+ $items['references-dialog/access/%/%'] = array( | |
+ 'page callback' => 'references_dialog_entity_access', | |
+ 'page arguments' => array(2,3), | |
+ 'access callback' => TRUE, | |
+ ); | |
return $items; | |
} | |
+function references_dialog_entity_access($entity_type, $entity) { | |
+ $entity = entity_load_single($entity_type, $entity); | |
+ return drupal_json_output(array( | |
+ 'access' => !empty($entity) && entity_access('update', $entity_type, $entity), | |
+ 'path' => url(references_dialog_get_admin_path($entity_type, 'edit', NULL, $entity)), | |
+ ) | |
+ ); | |
+} | |
+ | |
/** | |
* Implements hook_admin_paths(). | |
*/ | |
@@ -308,14 +334,27 @@ function references_dialog_process_widget(&$element) { | |
// Attach javascript and CSS needed. | |
$attached = references_dialog_attached(); | |
$element['#attached']['js'][] = $attached['js'][0]; | |
- $element['#attached']['js'][] = references_dialog_js_settings($element['#id'], array('format' => $dialog_widget['format'])); | |
+ $element['#attached']['js'][] = $attached['js'][1]; | |
+ | |
+ $js_settings = array( | |
+ 'format' => $dialog_widget['format'], | |
+ 'match' => !empty($dialog_widget['match']) ? $dialog_widget['match'] : NULL, | |
+ ); | |
+ if (isset($dialog_widget['entity_type'])) { | |
+ $js_settings['entity_type'] = $dialog_widget['entity_type']; | |
+ } | |
+ elseif (isset($dialog_widget['type_callback'])) { | |
+ $js_settings['entity_type'] = $dialog_widget['type_callback']($instance, $field); | |
+ } | |
$element['#attached']['css'][] = $attached['css'][0]; | |
$element['#attached']['library'][] = $attached['library'][0]; | |
- | |
$link_options = array('attributes' => array('class' => array('references-dialog-activate'))); | |
$dialog_links = array(); | |
foreach ($dialog_widget['operations'] as $operation => $settings) { | |
if (isset($widget_settings['references_dialog_' . $operation]) && $widget_settings['references_dialog_' . $operation]) { | |
+ if ($operation == 'edit') { | |
+ $js_settings['editable'] = TRUE; | |
+ } | |
$links = $settings['function']($element, $widget_settings, $field, $instance); | |
foreach ($links as $link) { | |
$link['attributes']['class'][] = $operation . '-dialog'; | |
@@ -323,6 +362,7 @@ function references_dialog_process_widget(&$element) { | |
} | |
} | |
} | |
+ $element['#attached']['js'][] = references_dialog_js_settings($element['#id'], $js_settings); | |
if (count($dialog_links)) { | |
// We add a div directly into the markup here since we really need it in order | |
// to make sure the javascript works. |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment