You are here

commerce_option_set_reference.module in Commerce Product Option 7

File

option_set_reference/commerce_option_set_reference.module
View source
<?php

/**
 * Implementation of hook_field_info();
 *
 */
function commerce_option_set_reference_field_info() {
  return array(
    'commerce_option_set_reference' => array(
      'label' => t('Option Set Reference'),
      'description' => t('This field stores the ID of the option set.'),
      'settings' => array(),
      'instance_settings' => array(),
      'default_widget' => 'commerce_option_set_reference_select_list',
      'default_formatter' => 'commerce_option_set_reference_form',
    ),
  );
}

/**
 * Implements hook_field_formatter_info().
 */
function commerce_option_set_reference_field_formatter_info() {
  return array(
    'commerce_option_set_reference_form' => array(
      'label' => t('Option Set: Form'),
      'description' => t('Display a form for the customer to enter the options.'),
      'field types' => array(
        'commerce_option_set_reference',
      ),
    ),
    'commerce_option_set_reference_attribute_view' => array(
      'label' => t('Option Set: Attribute View'),
      'description' => t('Display the options as attribute view..'),
      'field types' => array(
        'commerce_option_set_reference',
      ),
    ),
  );
}

/**
 * Implementation of hook_enable
 *
 * This is required to ensure that this module
 * hooks are executed after the ones of commerce_product_bundle.
 */
function commerce_option_set_reference_enable() {
  $weight = db_select('system', 's')
    ->fields('s', array(
    'weight',
  ))
    ->condition('name', 'commerce_product_bundle', '=')
    ->execute()
    ->fetchField();
  if (isset($weight)) {
    db_update('system')
      ->fields(array(
      'weight' => $weight + 1,
    ))
      ->condition('name', 'commerce_option_set_reference', '=')
      ->execute();
  }
}

/**
 * Check if the reference field is empty.
 */
function commerce_option_set_reference_field_is_empty($item, $field) {

  // set_id = 0 is empty too, which is exactly what we want.
  return empty($item['set_id']);
}
function commerce_option_set_reference_field_formatter_view($entity_type, $object, $field, $instance, $langcode, $items, $display) {
  $result = array();

  // Collect the list of product IDs.
  $product_ids = array();
  if ($display['type'] == 'commerce_option_set_reference_form') {

    /*foreach ($items as $delta => $item) {

          $option_set = commerce_option_set_load($item['set_id']);

          if(is_array($option_set)) {
            // Create new option:
            $option = entity_create('commerce_option', array('set_id' => $option_set['set_id']));
          }
        }*/
  }
  if ($display['type'] == 'commerce_option_set_reference_attribute_view') {
    foreach ($items as $delta => $item) {
      $option_set = commerce_option_set_load($item['set_id']);
      if (is_array($option_set)) {
      }
    }
  }
  return $result;
}

/**
 * Implements hook_field_widget_info().
 *
 * Defines widgets available for use with field types as specified in each
 * widget's $info['field types'] array.
 */
function commerce_option_set_reference_field_widget_info() {
  $widgets = array();

  // Define an autocomplete textfield widget for product referencing that works
  // like the Term Reference autocomplete widget.
  $widgets['commerce_option_set_reference_select_list'] = array(
    'label' => t('Select list'),
    'description' => t('Display the list of option sets as drop down.'),
    'field types' => array(
      'commerce_option_set_reference',
    ),
  );
  return $widgets;
}

/**
 * Implements hook_field_widget_form().
 */
function commerce_option_set_reference_field_widget_form(&$form, &$form_state, $field, $instance, $langcode, $items, $delta, $element) {
  if ($instance['widget']['type'] == 'commerce_option_set_reference_select_list') {
    $option_sets = commerce_option_get_sets();
    $options = array(
      '' => t('none'),
    );
    foreach ($option_sets as $set) {
      $options[$set->set_id] = $set->name;
    }
    $element['set_id'] = $element + array(
      '#type' => 'select',
      '#default_value' => isset($items[$delta]['set_id']) ? $items[$delta]['set_id'] : NULL,
      '#attributes' => array(
        'class' => array(
          'commerce-option-set-reference',
        ),
      ),
      '#options' => $options,
    );
  }
  return $element;
}

/**
 * Implementation of hook_form_alter()
 *
 * Here we modify the add to cart form.
 */
function commerce_option_set_reference_form_alter(&$form, &$form_state, $form_id) {
  if (strstr($form_id, 'commerce_cart_add_to_cart_form')) {
    if (isset($form_state['default_product'])) {
      $product_id = $form_state['default_product']->product_id;
    }
    elseif (isset($form_state['default_product_id'])) {
      $product_id = $form_state['default_product_id'];
    }
    elseif (isset($form_state['products'])) {
      $current_product = reset($form_state['products']);
      $product_id = $current_product->product_id;
    }
    else {
      return;
    }
    $current_product = commerce_product_load($product_id);
    $someFieldIsAdded = false;
    $options = array();
    if (isset($form_state['line_item']->line_item_id) && $form_state['line_item']->line_item_id > 0 && commerce_product_attributes_access_to_line_item($form_state['line_item']->line_item_id)) {

      // We need to reduce the number of options. We can only have one option per product
      // and per product field and line item. This limits us only in the fact that we can
      // have one option set per one option set reference field.
      foreach (commerce_option_load_by_line_item($form_state['line_item']->line_item_id) as $key => $option) {
        $options[$option->set_id][$option->product_id][$option->field_name][$option->field_delta] = $option;
      }
    }

    // Iterates of the fields of this product. We search for
    // option set reference fields.
    foreach ($current_product as $field_name => $field) {
      $field_info = field_info_field($field_name);
      $type = $field_info['type'];
      if ($type == 'commerce_option_set_reference') {
        $form[$field_name] = array(
          '#tree' => TRUE,
        );
        $lang_code = field_language('commerce_product', $current_product, $field_name);
        if (isset($field[$lang_code])) {
          foreach ($field[$lang_code] as $delta => $set_id) {
            if (count($options) > 0 && isset($options[$set_id['set_id']][$current_product->product_id][$field_name][$delta])) {
              $option = $options[$set_id['set_id']][$current_product->product_id][$field_name][$delta];
            }
            else {
              $option = entity_create('commerce_option', $set_id);
            }
            $form_state['commerce_option'][$field_name][$delta]['option'] = $option;
            $form[$field_name][$delta] = array(
              '#parents' => array(
                $field_name,
                $delta,
              ),
            );
            field_attach_form('commerce_option', $option, $form[$field_name][$delta], $form_state);
            $someFieldIsAdded = true;
          }
        }
      }
    }

    // TODO: Implement the multi options functionality to the bundle integration
    if (isset($form_state['bundle'])) {
      foreach ($form_state['bundle'] as $id => &$bundle_set) {
        $sub_product = $form_state['bundle'][$id]['default_product'];
        $sub_product_wrapper = entity_metadata_wrapper('commerce_product', $sub_product);
        $form[$id] = array(
          '#tree' => TRUE,
        );

        // Iterates of the fields of this product. We search for
        // option set reference fields.
        foreach ($sub_product as $field_name => $field) {
          $field_info = field_info_field($field_name);
          $type = $field_info['type'];
          $form[$id][$field_name] = array(
            '#tree' => TRUE,
          );
          if ($type == 'commerce_option_set_reference') {
            $lang_code = field_language('commerce_product', $sub_product, $field_name);
            if (isset($field[$lang_code])) {
              foreach ($field[$lang_code] as $delta => $set_id) {
                if (count($options) > 0 && isset($options[$set_id['set_id']][$current_product->product_id][$field_name][$delta])) {
                  $option = $options[$set_id['set_id']][$sub_product->product_id][$field_name][$delta];
                }
                else {
                  $option = entity_create('commerce_option', $set_id);
                }
                $form_state[$id]['commerce_option'][$field_name][$delta]['option'] = $option;
                $form[$id][$field_name][$delta] = array(
                  '#parents' => array(
                    $id,
                    $field_name,
                    $delta,
                  ),
                );
                field_attach_form('commerce_option', $option, $form[$id][$field_name][$delta], $form_state);
                $someFieldIsAdded = true;
              }
            }
          }
        }
      }
    }
    if ($someFieldIsAdded) {
      $form['#submit'][] = 'commerce_option_add_to_cart_submit';
    }
  }
}

/**
 * Cart submit callback function. This is required to create / update
 * the option related to the line item.
 *
 * @param $form Form array
 * @param $form_state The form state array.
 * @return void
 */
function commerce_option_add_to_cart_submit($form, $form_state) {
  if (isset($form_state['default_product'])) {
    $product_id = $form_state['default_product']->product_id;
  }
  elseif (isset($form_state['default_product_id'])) {
    $product_id = $form_state['default_product_id'];
  }
  elseif (isset($form_state['products'])) {
    $current_product = reset($form_state['products']);
    $product_id = $current_product->product_id;
  }
  else {
    return;
  }
  $current_product = commerce_product_load($product_id);
  foreach ($current_product as $field_name => $field) {
    $field_info = field_info_field($field_name);
    $type = $field_info['type'];
    if (isset($form_state['bundle'])) {
      foreach ($form_state['bundle'] as $id => &$bundle_set) {
        $sub_product = $form_state['bundle'][$id]['default_product'];
        $sub_product_wrapper = entity_metadata_wrapper('commerce_product', $sub_product);

        // Iterates of the fields of this product. We search for
        // option set reference fields.
        foreach ($sub_product as $field_name => $field) {
          $field_info = field_info_field($field_name);
          $type = $field_info['type'];
          if ($type == 'commerce_option_set_reference') {
            $lang_code = field_language('commerce_product', $sub_product, $field_name);
            foreach ($field[$lang_code] as $delta => $set_id) {
              $option = $form_state[$id]['commerce_option'][$field_name][$delta];

              // Notify field widgets.
              field_attach_submit('commerce_option', $option, $form[$id][$field_name][$delta], $form_state);

              //$option->line_item_id = $form_state['bundle_product_line_items'][$sub_product_wrapper->product_id->value()]->line_item_id;
              $option->line_item_id = $form_state['line_item']->line_item_id;
              $option->field_name = $field_name;
              $option->field_delta = $delta;
              $option->product_id = $sub_product->product_id;

              // Save the product.
              commerce_option_save($option);
            }
          }
        }
      }
    }
    else {
      if ($type == 'commerce_option_set_reference') {
        $lang_code = field_language('commerce_product', $current_product, $field_name);
        foreach ($field[$lang_code] as $delta => $set_id) {
          $option = $form_state['commerce_option'][$field_name][$delta]['option'];

          // Notify field widgets. // entity_form_submit_build_entity
          field_attach_submit('commerce_option', $option, $form[$field_name][$delta], $form_state);
          $option->line_item_id = $form_state['line_item']->line_item_id;
          $option->field_name = $field_name;
          $option->field_delta = $delta;
          $option->product_id = $current_product->product_id;

          // Save the product.
          commerce_option_save($option);
        }
      }
    }
  }
}