diff --git a/commerce_webform.rules.inc b/commerce_webform.rules.inc
index dd0f9c1..6c38e04 100644
--- a/commerce_webform.rules.inc
+++ b/commerce_webform.rules.inc
@@ -156,7 +156,6 @@ function commerce_webform_order_create($node, $webform_submission, $user) {
 
   // Add all the products chosen as line items to the order.
   _commerce_webform_create_order_line_items($product_details, $order_id, $uid, $node->nid, $webform_submission['sid']);
-
 }
 
 /**
@@ -263,19 +262,24 @@ function commerce_webform_order_update($node, $webform_submission, $user) {
     $wrapper = entity_metadata_wrapper('commerce_line_item', $line_item);
     $product = $wrapper->commerce_product->value();
     $order_id = $line_item->order_id;
-    if (isset($product_details[$product->product_id])) {
-      // Update this line item.
-      $product_detail = $product_details[$product->product_id];
-      $line_item->quantity = $product_detail->quantity;
-      $line_item->data['commerce_webform'] = array(
-        'choose_quantity' => $product_detail->choose_quantity,
-        'required' => $product_detail->required,
-      );
-      commerce_line_item_save($line_item);
 
-      // Update the webform submission for this product field.
-      $webform_submission_object = webform_get_submission($node->nid, $webform_submission['sid']);
-      commerce_webform_update_webform_submission_productfield($webform_submission_object, $order_id, $line_item->line_item_id, $product_detail->product->product_id, $product_detail->quantity, FALSE);
+    if (isset($product_details[$product->product_id])) {
+      // If the order has been paid for we do not want to modify it now.
+      $order = commerce_order_load($order_id);
+      if (empty($order->data['commerce_payment_order_paid_in_full_invoked'])) {
+        // Update this line item.
+        $product_detail = $product_details[$product->product_id];
+        $line_item->quantity = $product_detail->quantity;
+        $line_item->data['commerce_webform'] = array(
+          'choose_quantity' => $product_detail->choose_quantity,
+          'required' => $product_detail->required,
+        );
+        commerce_line_item_save($line_item);
+
+        // Update the webform submission for this product field.
+        $webform_submission_object = webform_get_submission($node->nid, $webform_submission['sid']);
+        commerce_webform_update_webform_submission_productfield($webform_submission_object, $order_id, $line_item->line_item_id, $product_detail->product->product_id, $product_detail->quantity, FALSE);
+      }
 
       // Remove this from the list of products to update.
       unset($product_details[$product->product_id]);
@@ -290,7 +294,6 @@ function commerce_webform_order_update($node, $webform_submission, $user) {
     // Create new line items for each new product on the submission.
     _commerce_webform_create_order_line_items($product_details, $order_id, $uid, $node->nid, $webform_submission['sid']);
   }
-
 }
 
 /**
diff --git a/productfield.inc b/productfield.inc
index db6198b..80c39ad 100644
--- a/productfield.inc
+++ b/productfield.inc
@@ -107,10 +107,12 @@ function _webform_edit_productfield($component) {
     '#title' => t('Minimum quantity:'),
     '#states' => array(
       'invisible' => array(
-        ':input[name="extra[choose_quantity]"]' => array('checked' => FALSE))),
+        ':input[name="extra[choose_quantity]"]' => array('checked' => FALSE)
+      )
+    ),
     '#default_value' => empty($component['extra']['choose_quantity_min']) ? 0 : $component['extra']['choose_quantity_min'],
     '#description' => t('Minimum quantity the user can select.'),
-       '#weight' => 6,
+    '#weight' => 6,
   );
 
   $form['extra']['choose_quantity_max'] = array(
@@ -119,7 +121,9 @@ function _webform_edit_productfield($component) {
     '#title' => t('Maximum quantity:'),
     '#states' => array(
       'invisible' => array(
-        ':input[name="extra[choose_quantity]"]' => array('checked' => FALSE))),
+        ':input[name="extra[choose_quantity]"]' => array('checked' => FALSE)
+      )
+    ),
     '#default_value' => empty($component['extra']['choose_quantity_max']) ? 0 : $component['extra']['choose_quantity_max'],
     '#description' => t('Maximum quantity the user can select. Leave at 0 if you would like to render a textfield instead of a select option.'),
     '#weight' => 7,
@@ -268,9 +272,14 @@ function _commerce_webform_productfield_expand($element) {
     foreach ($value as $id => $encoded_details) {
       $details = json_decode($encoded_details);
 
-      if ($details->paid && !user_access('alter product field on paid webform')) {
+      if (empty($details)) {
+        continue;
+      }
+
+      if (!empty($details->order_id)) {
         $disabled = TRUE;
       }
+
       if ($multiple) {
         $default_product_ids[] = $details->product_id;
         if ($choose_quantity) {
@@ -303,149 +312,114 @@ function _commerce_webform_productfield_expand($element) {
     }
   }
 
-  if (!$multiple || !$choose_quantity) {
+  if ($disabled) {
+    // The product has been paid for so should not be able to change it.
+    $element[] = array(
+      '#type' => 'value',
+      '#value' => $value,
+    );
+
+    $markup = array('#markup' => '<p>' . t('It is no longer possible to edit the products in this submission.') . '</p>');
+    $markup['#markup'] .= theme_webform_display_productfield(array('element' => $element));
+
+    $element[] = $markup;
+    $element['#title_display'] = 'before';
+  }
+  elseif (!$multiple || !$choose_quantity) {
     // Single quantity options.
-    if ($disabled) {
-      // The product has been paid for so should not be able to change it.
-      $rows = array();
-      $element[] = array(
-        '#type' => 'value',
-        '#value' => $default_product_ids,
-      );
+    $new_element = array(
+      '#type' => $aslist ? 'select' : ($multiple ? 'checkboxes' : 'radios'),
+      '#multiple' => $multiple,
+      '#size' => $aslist && $multiple ? 4 : 0,
+      '#title' => $name,
+      '#title_display' => 'none',
+      '#required' => $required,
+      '#description' => $description,
+      '#translatable' => array('title', 'description', 'options'),
+      '#options' => $options,
+      '#suffix' => $hidden_elements_html,
+      '#pre_render' => array(),
+      '#validated' => 'TRUE',
+      '#element_validate' => array('_webform_productfield_selection_validate'),
+    );
+
+    if (!empty($default_product_ids)) {
+      $new_element['#default_value'] = $default_product_ids;
+    }
 
-      $element[] = array(
-        '#type' => 'value',
-        '#value' => $default_quantities,
-      );
+    $element[] = $new_element;
 
-      if (is_array($default_product_ids)) {
-        foreach ($default_product_ids as $product_id) {
-          $rows[] = array($product_id, $options[$product_id], $default_quantities);
-        }
-      }
-      elseif ($default_product_ids > 0) {
-        $rows[] = array($default_product_ids, $options[$default_product_ids], $default_quantities);
+    if (!empty($choose_quantity) && !empty($element['#webform_component']['extra']['choose_quantity_max'])) {
+      $quantity_options = array();
+      foreach (range($element['#webform_component']['extra']['choose_quantity_min'], $element['#webform_component']['extra']['choose_quantity_max']) as $quantity_option) {
+        $quantity_options[$quantity_option] = $quantity_option;
       }
-
-      // @TODO - put this in a theme function.
-      $element['#markup'] = '<strong>' . $name . '</strong>';
-      $element['#markup'] .= theme('table', array('header' => array(t('Product ID'), t('Product name'), t('Quantity')), 'rows' => $rows));
-      $element['#markup'] .= '<p>' . t('This order has been completed and products choices cannot be edited online.') . '</p>';
+      $element[] = array(
+        '#type' => 'select',
+        '#options' => $quantity_options,
+        '#title' => t('@product quantity', array('@product' => $name)),
+        '#title_display' => 'after',
+        '#default_value' => is_array($default_quantities) ? $element['#webform_component']['extra']['choose_quantity_min'] : $default_quantities,
+        '#element_validate' => array('_webform_productfield_quantity_validate'),
+        '#weight' => 1,
+        '#attributes' => array('class' => array('productfield-quantity')),
+      );
     }
     else {
-      $new_element = array(
-        '#type' => $aslist ? 'select' : ($multiple ? 'checkboxes' : 'radios'),
-        '#multiple' => $multiple,
-        '#size' => $aslist && $multiple ? 4 : 0,
-        '#title' => $name,
-        '#title_display' => 'none',
+      $editable = empty($multiple) && !empty($choose_quantity);
+      $element[] = array(
+        '#type' => $editable ? 'textfield' : 'value',
+        '#title' => t('@product quantity', array('@product' => $name)),
+        '#default_value' => $choose_quantity ? (is_array($default_quantities) ? 1 : $default_quantities) : 1,
+        '#element_validate' => array('_webform_productfield_quantity_validate'),
         '#required' => $required,
-        '#description' => $description,
-        '#translatable' => array('title', 'description', 'options'),
-        '#options' => $options,
-        '#suffix' => $hidden_elements_html,
-        '#pre_render' => array(),
-        '#validated' => 'TRUE',
-        '#element_validate' => array('_webform_productfield_selection_validate'),
+        '#weight' => 1,
+        '#attributes' => array('class' => array('productfield-quantity')),
       );
-
-      if (!empty($default_product_ids)) {
-        $new_element['#default_value'] = $default_product_ids;
+    }
+  }
+  else {
+    // Product field is multiple and user can choose quantity.
+    $i = 1;
+    $element['multiple_product_quantities'] = array(
+      '#type' => 'fieldset',
+      '#title' => $name,
+      '#title_display' => $title_display,
+      '#element_validate' => array('_webform_productfield_required_multiple_quantities_validate'),
+      '#required' => $required,
+      '#weight' => 0,
+      // Hide title as fieldsets don't support #title_display.
+      '#pre_render' => array('webform_element_title_display'),
+    );
+
+    foreach ($options as $product_id => $product_name) {
+      if (empty($element['#webform_component']['extra']['choose_quantity_max'])) {
+        $element['multiple_product_quantities'][$product_id] = array(
+          '#type' => 'textfield',
+          '#title' => $product_name,
+          '#title_display' => 'after',
+          '#size' => 6,
+          '#default_value' => isset($default_quantities[$product_id]) ? $default_quantities[$product_id] : 0,
+          '#element_validate' => array('_webform_productfield_quantity_validate'),
+          '#weight' => $i++,
+        );
       }
-
-      $element[] = $new_element;
-
-      if (!empty($choose_quantity) && !empty($element['#webform_component']['extra']['choose_quantity_max'])) {
+      else {
         $quantity_options = array();
         foreach (range($element['#webform_component']['extra']['choose_quantity_min'], $element['#webform_component']['extra']['choose_quantity_max']) as $quantity_option) {
           $quantity_options[$quantity_option] = $quantity_option;
         }
-        $element[] = array(
+        $element['multiple_product_quantities'][$product_id] = array(
           '#type' => 'select',
           '#options' => $quantity_options,
-          '#title' => t('@product quantity', array('@product' => $name)),
+          '#title' => $product_name,
           '#title_display' => 'after',
-          '#default_value' => is_array($default_quantities) ? $element['#webform_component']['extra']['choose_quantity_min'] : $default_quantities,
+          '#default_value' => isset($default_quantities[$product_id]) ? $default_quantities[$product_id] : 0,
           '#element_validate' => array('_webform_productfield_quantity_validate'),
-          '#weight' => 1,
+          '#weight' => $i++,
           '#attributes' => array('class' => array('productfield-quantity')),
         );
       }
-      else {
-        $editable = empty($multiple) && !empty($choose_quantity);
-        $element[] = array(
-          '#type' => $editable ? 'textfield' : 'value',
-          '#title' => t('@product quantity', array('@product' => $name)),
-          '#default_value' => $choose_quantity ? (is_array($default_quantities) ? 1 : $default_quantities) : 1,
-          '#element_validate' => array('_webform_productfield_quantity_validate'),
-          '#required' => $required,
-          '#weight' => 1,
-          '#attributes' => array('class' => array('productfield-quantity')),
-        );
-      }
-
-    }
-  }
-  else {
-    // Product field is multiple and user can choose quantity.
-    $i = 1;
-
-    if ($disabled) {
-      $rows = array();
-      foreach ($default_quantities as $product_id => $quantity) {
-        $element[$product_id] = array(
-          '#type' => 'value',
-          '#value' => $quantity,
-        );
-        $rows[] = array($product_id, $options[$product_id], $quantity);
-      }
-
-      // @TODO - put this in a theme function.
-      $element['#markup'] = '<strong>' . $name . '</strong>';
-      $element['#markup'] .= theme('table', array('header' => array(t('Product ID'), t('Product name'), t('Quantity')), 'rows' => $rows));
-      $element['#markup'] .= '<p>' . t('This order has been completed and products choices cannot be edited online.') . '</p>';
-    }
-    else {
-      $element['multiple_product_quantities'] = array(
-        '#type' => 'fieldset',
-        '#title' => $name,
-        '#title_display' => $title_display,
-        '#element_validate' => array('_webform_productfield_required_multiple_quantities_validate'),
-        '#required' => $required,
-        '#weight' => 0,
-        // Hide title as fieldsets don't support #title_display.
-        '#pre_render' => array('webform_element_title_display'),
-      );
-
-      foreach ($options as $product_id => $product_name) {
-          if (empty($element['#webform_component']['extra']['choose_quantity_max'])) {
-            $element['multiple_product_quantities'][$product_id] = array(
-              '#type' => 'textfield',
-              '#title' => $product_name,
-              '#title_display' => 'after',
-              '#size' => 6,
-              '#default_value' => isset($default_quantities[$product_id]) ? $default_quantities[$product_id] : 0,
-              '#element_validate' => array('_webform_productfield_quantity_validate'),
-              '#weight' => $i++,
-            );
-          }
-          else {
-            $quantity_options = array();
-            foreach (range($element['#webform_component']['extra']['choose_quantity_min'], $element['#webform_component']['extra']['choose_quantity_max']) as $quantity_option) {
-              $quantity_options[$quantity_option] = $quantity_option;
-            }
-            $element['multiple_product_quantities'][$product_id] = array(
-              '#type' => 'select',
-              '#options' => $quantity_options,
-              '#title' => $product_name,
-              '#title_display' => 'after',
-              '#default_value' => isset($default_quantities[$product_id]) ? $default_quantities[$product_id] : 0,
-              '#element_validate' => array('_webform_productfield_quantity_validate'),
-              '#weight' => $i++,
-              '#attributes' => array('class' => array('productfield-quantity')),
-            );
-          }
-      }
     }
   }
 
@@ -482,8 +456,27 @@ function _webform_submit_productfield($component, $value) {
   $return = array();
   $multiple = $component['extra']['multiple'];
   $choose_quantity = !empty($component['extra']['choose_quantity']);
+  $keep_previous_submission = FALSE;
+
+  if (is_array($value)) {
+    // First check if we are dealing with a modified submission or if
+    // this is a resubmission, in which case we leave products unmodified.
+    foreach ($value as $product) {
+      if (!is_string($product) || is_numeric($product)) {
+        $keep_previous_submission = FALSE;
+        break;
+      }
+      else {
+        $keep_previous_submission = TRUE;
+      }
+    }
+  }
 
-  if ($multiple && $choose_quantity) {
+  if ($keep_previous_submission) {
+    // $value is an array of previously saved products.
+    $return = $value;
+  }
+  elseif ($multiple && $choose_quantity) {
     foreach ($value['multiple_product_quantities'] as $product_id => $quantity) {
       if ($quantity > 0) {
         $details = array(
@@ -518,7 +511,8 @@ function _webform_submit_productfield($component, $value) {
         }
       }
     }
-    else {
+    elseif (!empty($value[0]) && is_numeric($value[0])) {
+      // $value[0] is a product id.
       $details = array(
         'product_id' => $value[0],
         'quantity' => empty($value[0]) ? '0' : $value[1],
@@ -562,6 +556,8 @@ function theme_webform_display_productfield($variables) {
     }
   }
 
+  $element['#format'] = empty($element['#format']) ? 'html' : $element['#format'];
+
   if ($element['#format'] == 'html') {
     $output = count($items) > 1 ? theme('item_list', array('items' => $items)) : (isset($items[0]) ? $items[0] : t('Not selected'));
   }
@@ -610,7 +606,10 @@ function _webform_analysis_productfield($component, $sids = array(), $single = F
         $rows[$submission->product_id . '_' . $paid_display_option][1]++;
       }
       else {
-        $rows[$submission->product_id . '_' . $paid_display_option] = array($display_option . ' (' . _webform_filter_xss($paid_display_option) . ')', 1);
+        $rows[$submission->product_id . '_' . $paid_display_option] = array(
+          $display_option . ' (' . _webform_filter_xss($paid_display_option) . ')',
+          1
+        );
       }
     }
   }
