diff --git a/acdx_entityreference/acdx_entityreference.info b/acdx_entityreference/acdx_entityreference.info
new file mode 100644
index 0000000..d510d40
--- /dev/null
+++ b/acdx_entityreference/acdx_entityreference.info
@@ -0,0 +1,11 @@
+; $Id$
+name = Autocomplete Deluxe Entity References Widget
+description = Autocomplete Deluxe widget implementation for entity references.
+package = User interface
+project = acdx_references
+version = VERSION
+core = 7.x
+files[] = acdx_entityreference.module
+dependencies[] = autocomplete_deluxe
+dependencies[] = entityreference
+dependencies[] = entity
diff --git a/acdx_entityreference/acdx_entityreference.module b/acdx_entityreference/acdx_entityreference.module
new file mode 100644
index 0000000..aeaae6e
--- /dev/null
+++ b/acdx_entityreference/acdx_entityreference.module
@@ -0,0 +1,254 @@
+<?php
+// $Id$
+
+/**
+ * Implements hook_field_widget_info().
+ */
+function acdx_entityreference_field_widget_info() {
+  $widgets['entityreference_autocomplete_deluxe'] = array(
+    'label' => t('Autocomplete Deluxe'),
+    'description' => t('An autocomplete text field - with deluxe behavior.'),
+    'field types' => array('entityreference'),
+    'settings' => array(
+      'match_operator' => 'CONTAINS',
+      'size' => 60,
+      // We don't have a default here, because it's not the same between
+      // the two widgets, and the Field API doesn't update default
+      // settings when the widget changes.
+      'path' => '',
+    ),
+  );
+  $widgets['entityreference_autocomplete_deluxe_tags'] = array(
+    'label' => t('Autocomplete Deluxe (tags)'),
+    'description' => t('An autocomplete text field with deluxe tagging behavior.'),
+    'field types' => array('entityreference'),
+    'settings' => array(
+      'match_operator' => 'CONTAINS',
+      'size' => 60,
+      'create_bundle' => '',
+    ),
+    'behaviors' => array(
+      'multiple values' => FIELD_BEHAVIOR_CUSTOM,
+    ),
+  );
+
+  return $widgets;
+}
+
+/**
+ * Implements hook_field_widget_info_alter().
+ */
+function acdx_entityreference_field_widget_info_alter(&$info) {
+  $info['options_select']['field types'][] = 'entityreference';
+  $info['options_buttons']['field types'][] = 'entityreference';
+}
+
+
+/**
+ * Implements hook_field_widget_settings_form().
+ */
+function acdx_entityreference_field_widget_settings_form($field, $instance) {
+  $widget = $instance['widget'];
+  $settings = $widget['settings'] + field_info_widget_settings($widget['type']);
+
+  $form = array();
+
+  if (in_array($widget['type'], array('entityreference_autocomplete_deluxe', 'entityreference_autocomplete_deluxe_tags'))) {
+    $form['match_operator'] = array(
+      '#type' => 'select',
+      '#title' => t('Autocomplete matching'),
+      '#default_value' => $settings['match_operator'],
+      '#options' => array(
+        'STARTS_WITH' => t('Starts with'),
+        'CONTAINS' => t('Contains'),
+      ),
+      '#description' => t('Select the method used to collect autocomplete suggestions. Note that <em>Contains</em> can cause performance issues on sites with thousands of nodes.'),
+    );
+    $form['size'] = array(
+      '#type' => 'textfield',
+      '#title' => t('Size of textfield'),
+      '#default_value' => $settings['size'],
+      '#element_validate' => array('_element_validate_integer_positive'),
+      '#required' => TRUE,
+    );
+    $info = entity_get_info($field['settings']['target_type']);
+    $options = array('' => t("-- Don't create --"));
+    foreach ($info['bundles'] as $bundle_name => $bundle) {
+      $options[$bundle_name] = $bundle['label'];
+    }
+    $form['create_bundle'] = array(
+      '#type' => 'select',
+      '#access' => ($widget['type'] == 'entityreference_autocomplete_deluxe_tags'),
+      '#title' => t('Create new entities'),
+      '#description' => t("When a tag is entered that doesn't match any existing entity, you can create a new entity.  Select a bundle to use for the newly created entity."),
+      '#options' => $options,
+      '#default_value' => $settings['create_bundle'],
+    );
+  }
+
+  return $form;
+}
+
+
+/**
+ * Implements hook_field_widget_form().
+ */
+function acdx_entityreference_field_widget_form(&$form, &$form_state, $field, $instance, $langcode, $items, $delta, $element) {
+  $handler = entityreference_get_handler($field);
+  switch ($instance['widget']['type']) {
+    case 'entityreference_autocomplete_deluxe':
+    case 'entityreference_autocomplete_deluxe_tags':
+      if ($instance['widget']['type'] == 'entityreference_autocomplete_deluxe') {
+        // We let the Field API handles multiple values for us, only take
+        // care of the one matching our delta.
+        if (isset($items[$delta])) {
+          $items = array($items[$delta]);
+        }
+        else {
+          $items = array();
+        }
+      }
+      elseif ($instance['widget']['type'] == 'entityreference_autocomplete_deluxe_tags') {
+        $element['#element_validate'] = array('_acdx_entityreference_autocomplete_tags_validate');
+        $element['#multiple'] = TRUE;
+      }
+
+      $entity_ids = array();
+      $entity_labels = array();
+
+      // Build an array of entities ID.
+      foreach ($items as $item) {
+        $entity_ids[] = $item['target_id'];
+      }
+
+      // Load those entities and loop through them to extract their labels.
+      $entities = entity_load($field['settings']['target_type'], $entity_ids);
+
+      foreach ($entities as $entity_id => $entity) {
+        $label = $handler->getLabel($entity);
+        $key = "$label ($entity_id)";
+        // Labels containing commas or quotes must be wrapped in quotes.
+        if (strpos($key, ',') !== FALSE || strpos($key, '"') !== FALSE) {
+          $key = '"' . str_replace('"', '""', $key) . '"';
+        }
+        $entity_labels[] = $key;
+      }
+      $path = !empty($instance['widget']['settings']['path']) ? $instance['widget']['settings']['path'] : 'entityreference/autocomplete/single';
+      $element += array(
+        '#type' => 'autocomplete_deluxe',
+        '#maxlength' => 1024,
+        '#default_value' => implode(', ', $entity_labels),
+        '#autocomplete_deluxe_path' => url($path . '/' . $field['field_name'] . '/' . $instance['entity_type'] . '/' . $instance['bundle'], array('absolute' => TRUE)),
+        '#size' => $instance['widget']['settings']['size'],
+        '#element_validate' => array('_entityreference_autocomplete_validate'),
+        '#autocomplete_min_length' => 1,
+      );
+      if ($instance['widget']['type'] == 'entityreference_autocomplete_deluxe') {
+        return array('target_id' => $element);
+      }
+      return $element;
+  }
+}
+
+function _acdx_entityreference_autocomplete_validate($element, &$form_state, $form) {
+  // If a value was entered into the autocomplete...
+  $value = '';
+  if (!empty($element['#value'])) {
+    // Take "label (entity id)', match the id from parenthesis.
+    if (preg_match("/.+\((\d+)\)/", $element['#value'], $matches)) {
+      $value = $matches[1];
+    }
+  }
+  // Update the value of this element so the field can validate the product IDs.
+  form_set_value($element, $value, $form_state);
+}
+
+function _acdx_entityreference_autocomplete_tags_validate($element, &$form_state, $form) {
+  $value = array();
+  if (preg_match_all('/"(?:""|[^"])*"|[^",]+/', $element['value_field']['#value'], $matches)) {
+    $entity = &$form_state[$form['#entity_type']];
+    $entity->acdx_entityreference = array();
+    foreach ($matches[0] as $match) {
+      if (preg_match('/\((\d+)\)"?$/', $match, $id_matches)) {
+        $value[]['target_id'] = $id_matches[1];
+      }
+      else {
+        $entity->acdx_entityreference[$element['#field_name']][] = array(
+          'label' => $match,
+          'parents' => $element['#parents'],
+        );
+      }
+    }
+  }
+  form_set_value($element, $value, $form_state);
+}
+
+/**
+ * Implements hook_field_attach_presave().
+ */
+function acdx_entityreference_field_attach_presave($entity_type, $entity) {
+  $entity_info = entity_get_info($entity_type);
+  $bundle_name = $entity->{$entity_info['entity keys']['bundle']};
+  foreach (field_info_instances($entity_type, $bundle_name) as $field_info) {
+    if ($field_info['widget']['type'] == 'entityreference_autocomplete_deluxe_tags' && $field_info['widget']['settings']['create_bundle'] != '') {
+      $field_name = $field_info['field_name'];
+      $field = field_info_field($field_name);
+      if (!empty($entity->acdx_entityreference[$field_name])) {
+        foreach ($entity->acdx_entityreference[$field_name] as $autocreate) {
+          $parents = $autocreate['parents'];
+          array_shift($parents); // field name, which we already know
+          $ptr = &$entity->{$field_name};
+          foreach ($parents as $parent) {
+            $ptr = &$ptr[$parent];
+          }
+
+          $target_id = _acdx_entityreference_create($field['settings']['target_type'], $field_info['widget']['settings']['create_bundle'], $autocreate['label']);
+
+          $ptr[] = array(
+            'target_type' => $field['settings']['target_type'],
+            'target_id' => $target_id,
+          );
+        }
+      }
+    }
+  }
+}
+
+function _acdx_entityreference_create($entity_type, $bundle_name, $label) {
+  $entity_info = entity_get_info($entity_type);
+  $entity_init = array(
+    $entity_info['entity keys']['bundle'] => $bundle_name,
+    $entity_info['entity keys']['label'] => $label,
+  );
+
+  // Allow modules to tweak this for entity types that need special treatment.
+  drupal_alter('acdx_entityreference_create', $entity_init, $entity_type);
+
+  $entity = entity_create($entity_type, $entity_init);
+
+  // Nodes have per-bundle create permissions, and we can't simply pass a
+  // skeleton node object to entity_access() as it would get cached in the
+  // wrong place due to some assumptions that node_access() makes about its
+  // parameters.
+  $access = ($entity_type == 'node') ? node_access('create', $bundle_name) : entity_access('create', $entity_type);
+
+  if ($access) {
+    entity_save($entity_type, $entity);
+    return $entity->{$entity_info['entity keys']['id']};
+  }
+}
+
+/**
+ * Implements hook_acdx_entityreference_create_alter().
+ *
+ * Handle some special cases for core entities.
+ */
+function acdx_entityreference_acdx_entityreference_create_alter(&$entity_init, $entity_type) {
+  global $user;
+  if ($entity_type == 'node' && $user->uid) {
+    $entity_init['uid'] = $user->uid;
+  }
+  if ($entity_type == 'taxonomy_term' && $vocabulary = taxonomy_vocabulary_machine_name_load($entity_init['vocabulary_machine_name'])) {
+    $entity_init['vid'] = $vocabulary->vid;
+  }
+}
