more module updates

This commit is contained in:
Bachir Soussi Chiadmi
2015-04-20 18:02:17 +02:00
parent 37fbabab56
commit 7c85261e56
100 changed files with 6518 additions and 913 deletions

View File

@@ -1,10 +1,10 @@
.addressfield-container-inline > div.form-item {
div.addressfield-container-inline > div.form-item {
float: right;
margin-right: 0;
margin-left: 1em;
}
.addressfield-container-inline.country-GB > div.form-item {
div.addressfield-container-inline.country-GB > div.form-item {
margin-left: auto;
margin-right: 0;
}

View File

@@ -0,0 +1,442 @@
<?php
/**
* Contains the predefined address formats.
*
* Derived from Google's dataset: https://i18napis.appspot.com/address.
*/
/**
* Returns the address format for the given country code.
*
* @param $country_code
* The country code for which the address format should be returned.
*
* @return
* The address format array with the following keys:
* - used_fields: An array of fields used by this format. Possible values:
* 'dependent_locality', 'locality', 'administrative_area', 'postal_code'.
* - required_fields: An array of required fields. See "used_fields".
* - dependent_locality_label: The label for the dependent locality field.
* - locality_label: The label for the locality field.
* - administrative_area_label: The label for the administrative area field.
* - postal_code_label: The label for the postal code field.
* - render_administrative_area_value: True if the value should be rendered
* instead of the ISO code. US example: California instead of CA.
* Only relevant for countries with predefined administrative areas.
*/
function addressfield_get_address_format($country_code) {
$default_values = array(
'used_fields' => array('locality'),
'required_fields' => array('locality'),
'dependent_locality_label' => t('Suburb'),
'locality_label' => t('City'),
'administrative_area_label' => t('Province'),
'postal_code_label' => t('Postal code'),
'render_administrative_area_value' => FALSE,
);
$address_formats = array();
// These formats differ from the default only by the presence of the
// postal code in 'used_fields'.
$countries_with_optional_postal_code = array(
'AC', 'AD', 'AL', 'AZ', 'BA', 'BB', 'BD', 'BG', 'BH', 'BM', 'BN', 'BT',
'CR', 'CY', 'CZ', 'DO', 'DZ', 'EC', 'EH', 'ET', 'FO', 'GE', 'GN', 'GT',
'GW', 'HR', 'HT', 'HU', 'IL', 'IS', 'JO', 'KE', 'KG', 'KH', 'KW', 'LA',
'LA', 'LB', 'LK', 'LR', 'LS', 'MA', 'MC', 'MD', 'ME', 'MG', 'MK', 'MM',
'MT', 'MU', 'MV', 'NE', 'NP', 'OM', 'PK', 'PY', 'RO', 'RS', 'SA', 'SI',
'SK', 'SN', 'SZ', 'TA', 'TJ', 'TM', 'TN', 'VA', 'VC', 'VG', 'XK', 'ZM',
);
foreach ($countries_with_optional_postal_code as $code) {
$address_formats[$code] = array(
'used_fields' => array('locality', 'postal_code'),
);
}
// These formats differ from the default only by the presence of the
// postal code in 'used_fields' and 'required_fields'.
$countries_with_required_postal_code = array(
'AT', 'AX', 'BE', 'BL', 'CH', 'DE', 'DK', 'FI', 'FK', 'FR', 'GF', 'GG',
'GL', 'GP', 'GR', 'GS', 'IM', 'IO', 'JE', 'LI', 'LU', 'MF', 'MQ', 'NC',
'NL', 'NO', 'PL', 'PM', 'PN', 'PT', 'RE', 'SE', 'SH', 'SJ', 'TC', 'WF',
'YT',
);
foreach ($countries_with_required_postal_code as $code) {
$address_formats[$code] = array(
'used_fields' => array('locality', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
);
}
$address_formats['AE'] = array(
'used_fields' => array('administrative_area'),
'administrative_area_label' => t('Emirate'),
);
$address_formats['AM'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['AR'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'render_administrative_area_value' => TRUE,
);
$address_formats['AS'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['AU'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'locality_label' => t('City/Suburb'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('Postcode'),
);
$address_formats['BR'] = array(
'used_fields' => array('dependent_locality', 'locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'dependent_locality_label' => t('Neighborhood'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
);
$address_formats['BS'] = array(
'used_fields' => array('locality', 'administrative_area'),
'administrative_area_label' => t('Island'),
);
$address_formats['BY'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['CA'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['CC'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['CL'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'render_administrative_area_value' => TRUE,
);
$address_formats['CN'] = array(
'used_fields' => array('dependent_locality', 'locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area'),
'dependent_locality_label' => t('District'),
);
$address_formats['CO'] = array(
'used_fields' => array('locality', 'administrative_area'),
'administrative_area_label' => t('Department', array(), array('context' => 'Territory of a country')),
);
$address_formats['CV'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('Island'),
);
$address_formats['CX'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['EG'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('Governorate'),
);
$address_formats['EE'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'administrative_area_label' => t('County'),
);
$address_formats['ES'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'render_administrative_area_value' => TRUE,
);
$address_formats['FM'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['GB'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'locality_label' => t('Town/City'),
'administrative_area_label' => t('County'),
'postal_code_label' => t('Postcode'),
);
$address_formats['GI'] = array(
'used_fields' => array('postal_code'),
);
$address_formats['GU'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['HK'] = array(
'used_fields' => array('locality', 'administrative_area'),
'required_fields' => array('administrative_area'),
'locality_label' => t('District'),
'administrative_area_label' => t('Area', array(), array('context' => 'Territory of a country')),
);
$address_formats['HN'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area'),
);
$address_formats['ID'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'locality_label' => t('City/Regency'),
'render_administrative_area_value' => TRUE,
);
$address_formats['IE'] = array(
'used_fields' => array('locality', 'administrative_area'),
'locality_label' => t('Town/City'),
'administrative_area_label' => t('County'),
'render_administrative_area_value' => TRUE,
);
$address_formats['IN'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('PIN code'),
'render_administrative_area_value' => TRUE,
);
$address_formats['IQ'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area'),
);
$address_formats['IR'] = array(
'used_fields' => array('dependent_locality', 'locality', 'administrative_area', 'postal_code'),
'dependent_locality_label' => t('Neighborhood'),
);
$address_formats['IT'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['JM'] = array(
'used_fields' => array('locality', 'administrative_area'),
'required_fields' => array('locality', 'administrative_area'),
'administrative_area_label' => t('Parish', array(), array('context' => 'Territory of a country')),
'render_administrative_area_value' => TRUE,
);
$address_formats['JP'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('Prefecture'),
'render_administrative_area_value' => TRUE,
);
$address_formats['KI'] = array(
'used_fields' => array('locality', 'administrative_area'),
'administrative_area_label' => t('Island'),
);
$address_formats['KN'] = array(
'used_fields' => array('locality', 'administrative_area'),
'required_fields' => array('locality', 'administrative_area'),
'administrative_area_label' => t('Island'),
);
$address_formats['KR'] = array(
'used_fields' => array('dependent_locality', 'locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'dependent_locality_label' => t('District'),
);
$address_formats['KY'] = array(
'used_fields' => array('administrative_area', 'postal_code'),
'required_fields' => array('administrative_area'),
'administrative_area_label' => t('Island'),
);
$address_formats['KZ'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('Region', array(), array('context' => 'Territory of a country')),
);
$address_formats['LT'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'administrative_area_label' => t('County'),
);
$address_formats['LV'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'administrative_area_label' => t('Municipality'),
);
$address_formats['MH'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['MN'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['MP'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['MX'] = array(
'used_fields' => array('dependent_locality', 'locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'dependent_locality_label' => t('Neighborhood'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
);
$address_formats['MY'] = array(
'used_fields' => array('dependent_locality', 'locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'dependent_locality_label' => t('Village / Township'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'render_administrative_area_value' => TRUE,
);
$address_formats['MZ'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['NF'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['NG'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
);
$address_formats['NI'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('Department', array(), array('context' => 'Territory of a country')),
);
$address_formats['NR'] = array(
'used_fields' => array('administrative_area'),
'required_fields' => array('administrative_area'),
'administrative_area_label' => t('District'),
);
$address_formats['NZ'] = array(
'used_fields' => array('dependent_locality', 'locality', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'locality_label' => t('Town/City'),
'postal_code_label' => t('Postcode'),
);
$address_formats['PA'] = array(
'used_fields' => array('locality', 'administrative_area'),
);
$address_formats['PE'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'locality_label' => t('District'),
'administrative_area_label' => t('Department', array(), array('context' => 'Territory of a country')),
);
$address_formats['PF'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('Island'),
);
$address_formats['PG'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area'),
);
$address_formats['PH'] = array(
'used_fields' => array('dependent_locality', 'locality', 'administrative_area', 'postal_code'),
);
$address_formats['PR'] = array(
'used_fields' => array('locality', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'postal_code_label' => t('ZIP code'),
);
$address_formats['PW'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['RU'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
);
$address_formats['SC'] = array(
'used_fields' => array('locality', 'administrative_area'),
'administrative_area_label' => t('Island'),
);
$address_formats['SG'] = array(
'used_fields' => array('postal_code'),
'required_fields' => array('postal_code'),
);
$address_formats['SM'] = array(
'used_fields' => array('locality', 'postal_code'),
'required_fields' => array('postal_code'),
);
$address_formats['SO'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area'),
);
$address_formats['SR'] = array(
'used_fields' => array('locality', 'administrative_area'),
);
$address_formats['SV'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area'),
);
$address_formats['TH'] = array(
'used_fields' => array('dependent_locality', 'locality', 'administrative_area', 'postal_code'),
);
$address_formats['TR'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'locality_label' => t('District'),
'render_administrative_area_value' => TRUE,
);
$address_formats['TV'] = array(
'used_fields' => array('locality', 'administrative_area'),
'administrative_area_label' => t('Island'),
);
$address_formats['TW'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['UA'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
'administrative_area_label' => t('Region', array(), array('context' => 'Territory of a country')),
);
$address_formats['UM'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['US'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['UY'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['UZ'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['VE'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area'),
'render_administrative_area_value' => TRUE,
);
$address_formats['VI'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
'required_fields' => array('locality', 'administrative_area', 'postal_code'),
'administrative_area_label' => t('State', array(), array('context' => 'Territory of a country')),
'postal_code_label' => t('ZIP code'),
);
$address_formats['VN'] = array(
'used_fields' => array('locality', 'administrative_area', 'postal_code'),
);
$address_formats['ZA'] = array(
'used_fields' => array('dependent_locality', 'locality', 'postal_code'),
'required_fields' => array('locality', 'postal_code'),
);
// Allow other modules to alter the formats.
drupal_alter('addressfield_address_formats', $address_formats);
if (isset($address_formats[$country_code])) {
$format = $address_formats[$country_code] + $default_values;
}
else {
// There is no predefined address format for the requested country,
// but the defaults should work fine.
$format = $default_values;
}
return $format;
}

View File

@@ -29,6 +29,72 @@ function CALLBACK_addressfield_format_callback(&$format, $address, $context = ar
// No example.
}
/**
* Allows modules to alter the default values for an address field.
*
* @param $default_values
* The array of default values. The country is populated from the
* 'default_country' widget setting.
* @param $context
* An array with the following keys:
* - field: The field array.
* - instance: The instance array.
* - address: The current address values. Allows for per-country defaults.
*/
function hook_addressfield_default_values_alter(&$default_values, $context) {
// If no other default country was provided, set it to France.
// Note: you might want to check $context['instance']['required'] and
// skip setting the default country if the field is optional.
if (empty($default_values['country'])) {
$default_values['country'] = 'FR';
}
// Determine the country for which other defaults should be provided.
$selected_country = $default_values['country'];
if (isset($context['address']['country'])) {
$selected_country = $context['address']['country'];
}
// Add defaults for the US.
if ($selected_country == 'US') {
$default_values['locality'] = 'New York';
$default_values['administrative_area'] = 'NY';
}
}
/**
* Allows modules to alter the predefined address formats.
*
* @param $address_formats
* The array of all predefined address formats.
*
* @see addressfield_get_address_format()
*/
function hook_addressfield_address_formats_alter(&$address_formats) {
// Remove the postal_code from the list of required fields for China.
$address_formats['CN']['required_fields'] = array('locality', 'administrative_area');
}
/**
* Allows modules to alter the predefined administrative areas.
*
* @param $administrative_areas
* The array of all predefined administrative areas.
*
* @see addressfield_get_administrative_areas()
*/
function hook_addressfield_administrative_areas_alter(&$administrative_areas) {
// Alter the label of the Spanish administrative area with the iso code PM.
$administrative_areas['ES']['PM'] = t('Balears / Baleares');
// Add administrative areas for imaginary country XT, keyed by their
// imaginary ISO codes.
$administrative_areas['XT'] = array(
'A' => t('Aland'),
'B' => t('Bland'),
);
}
/**
* Allows modules to add arbitrary AJAX commands to the array returned from the
* standard address field widget refresh.

View File

@@ -45,7 +45,7 @@ function _addressfield_sample_addresses() {
if (is_resource($handle)) {
$addresses = array();
while (($buffer = fgets($handle)) !== false) {
list($country, $administrative_area, $sub_administrative_area, $locality, $dependent_locality, $postal_code, $thoroughfare, $premise) = explode("\t", $buffer);
list($country, $administrative_area, $sub_administrative_area, $locality, $dependent_locality, $postal_code, $thoroughfare, $premise, $sub_premise) = explode("\t", $buffer);
$fields[] = array(
'country' => ($country == 'NULL') ? NULL : trim($country),
'administrative_area' => ($administrative_area == 'NULL') ? NULL : trim($administrative_area),
@@ -55,6 +55,7 @@ function _addressfield_sample_addresses() {
'postal_code' => ($postal_code == 'NULL') ? NULL : trim($postal_code),
'thoroughfare' => ($thoroughfare == 'NULL') ? NULL : trim($thoroughfare),
'premise' => ($premise == 'NULL') ? NULL : trim($premise),
'sub_premise' => ($sub_premise == 'NULL') ? NULL : trim($sub_premise),
);
}
}

View File

@@ -5,11 +5,13 @@ package = Fields
dependencies[] = ctools
files[] = addressfield.migrate.inc
files[] = views/addressfield_views_handler_field_country.inc
files[] = views/addressfield_views_handler_filter_country.inc
; Information added by drupal.org packaging script on 2013-05-07
version = "7.x-1.0-beta4"
; Information added by Drupal.org packaging script on 2015-01-16
version = "7.x-1.0"
core = "7.x"
project = "addressfield"
datestamp = "1367945112"
datestamp = "1421426885"

View File

@@ -184,3 +184,33 @@ function addressfield_update_7000() {
}
}
}
/**
* Sets the value of the new "Default country" setting.
*/
function addressfield_update_7001() {
$address_fields = array();
foreach (field_info_fields() as $field_name => $field_info) {
if ($field_info['type'] == 'addressfield') {
$address_fields[$field_name] = $field_name;
}
}
foreach (field_info_instances() as $entity_type => $bundles) {
foreach ($bundles as $bundle_name => $instances) {
foreach (array_intersect_key($instances, $address_fields) as $field_name => $instance) {
// Optional fields get the None default. Required fields get the
// previously selected default country.
$default_country = '';
if (!empty($instance['required']) && !empty($instance['default_value'])) {
$default_country = $instance['default_value']['country'];
}
$instance['widget']['settings']['default_country'] = $default_country;
unset($instance['default_value']);
field_update_instance($instance);
}
}
}
}

View File

@@ -0,0 +1,172 @@
<?php
/**
* @file
* Base integration with the Migrate API class.
*/
/**
* Implements hook_migrate_api().
*/
function addressfield_migrate_api() {
$api = array(
'api' => 2,
'field handlers' => array('MigrateAddressFieldHandler'),
);
return $api;
}
/**
* Primary value passed to this field must be the two letter ISO country code of
* the address.
*
* Arguments are used to specify all the other values:
* 'administrative_area' - The administrative area of this address. (i.e. State/Province)
* 'sub_administrative_area' - The sub administrative area of this address.
* 'locality' - The locality of this address. (i.e. City)
* 'dependent_locality' - The dependent locality of this address.
* 'postal_code' - The postal code of this address.
* 'thoroughfare' - The thoroughfare of this address. (i.e. Street address)
* 'premise' - The premise of this address. (i.e. Apartment / Suite number)
* 'sub_premise' - The sub_premise of this address.
* 'organisation_name' - Contents of a primary OrganisationName element in the xNL XML.
* 'name_line' - Contents of a primary NameLine element in the xNL XML.
* 'first_name' - Contents of the FirstName element of a primary PersonName element in the xNL XML.
* 'last_name' - Contents of the LastName element of a primary PersonName element in the xNL XML.
* 'data' - Additional data for this address.
*
* Add the source field mappings to the argument array then add null mappings to
* avoid having fields flagged as as unmapped:
* @code
* // The country should be passed in as the primary value.
* $this->addFieldMapping('field_address', 'profile_country');
* $this->addFieldMapping('field_address:thoroughfare', 'profile_address');
* $this->addFieldMapping('field_address:locality', 'profile_city');
* $this->addFieldMapping('field_address:administrative_area', 'profile_state');
* @endcode
*/
class MigrateAddressFieldHandler extends MigrateFieldHandler {
public function __construct() {
$this->registerTypes(array('addressfield'));
}
/**
* Provide subfields for the addressfield columns.
*/
public function fields() {
// Declare our arguments to also be available as subfields.
$fields = array(
'administrative_area' => t('<a href="@doc">The administrative area of ' .
'this address (i.e. State/Province)</a>',
array('@doc' => 'http://drupal.org/node/1996546#administrative_area')),
'sub_administrative_area' => t('<a href="@doc">The sub administrative ' .
'area of this address</a>',
array('@doc' => 'http://drupal.org/node/1996546#sub_administrative_area')),
'locality' => t('<a href="@doc">The locality of this address (i.e. ' .
'City)</a>',
array('@doc' => 'http://drupal.org/node/1996546#locality')),
'dependent_locality' => t('<a href="@doc">The dependent locality of ' .
'this address</a>',
array('@doc' => 'http://drupal.org/node/1996546#dependent_locality')),
'postal_code' => t('<a href="@doc">The postal code of this address</a>',
array('@doc' => 'http://drupal.org/node/1996546#postal_code')),
'thoroughfare' => t('<a href="@doc">The thoroughfare of this address ' .
'(i.e. Street address)</a>',
array('@doc' => 'http://drupal.org/node/1996546#thoroughfare')),
'premise' => t('<a href="@doc">The premise of this address (i.e. Apartment / Suite number)</a>',
array('@doc' => 'http://drupal.org/node/1996546#premise')),
'sub_premise' => t('<a href="@doc">The sub_premise of this address</a>',
array('@doc' => 'http://drupal.org/node/1996546#sub_premise')),
'organisation_name' => t('<a href="@doc">Contents of a primary ' .
'OrganisationName element in the xNL XML</a>',
array('@doc' => 'http://drupal.org/node/1996546#organisation_name')),
'name_line' => t('<a href="@doc">Contents of a primary NameLine element ' .
'in the xNL XML</a>',
array('@doc' => 'http://drupal.org/node/1996546#name_line')),
'first_name' => t('<a href="@doc">Contents of the FirstName element of ' .
'a primary PersonName element in the xNL XML</a>',
array('@doc' => 'http://drupal.org/node/1996546#first_name')),
'last_name' => t('<a href="@doc">Contents of the LastName element of a ' .
'primary PersonName element in the xNL XML</a>',
array('@doc' => 'http://drupal.org/node/1996546#last_name')),
'data' => t('<a href="@doc">Additional data for this address</a>',
array('@doc' => 'http://drupal.org/node/1996546#data')),
);
return $fields;
}
/**
* Implements MigrateFieldHandler::prepare().
*
* @param $entity
* @param array $field_info
* @param array $instance
* @param array $values
*
* @return null
*/
public function prepare($entity, array $field_info, array $instance,
array $values) {
$arguments = array();
if (isset($values['arguments'])) {
$arguments = array_filter($values['arguments']);
unset($values['arguments']);
}
$language = $this->getFieldLanguage($entity, $field_info, $arguments);
// Setup the standard Field API array for saving.
$delta = 0;
foreach ($values as $value) {
$return[$language][$delta] = array('country' => $value)
+ $this->prepareArguments($arguments, $field_info, $delta);
$delta++;
}
return isset($return) ? $return : NULL;
}
/**
* Builds an array with additional data for the current $delta.
*
* @param array $arguments
* @param array $field_info
* @param $delta
*
* @return array
*/
protected function prepareArguments(array $arguments, array $field_info, $delta) {
$result = array();
$data = array();
foreach ($arguments as $column_key => $column_value) {
$value = NULL;
if (is_array($arguments[$column_key])) {
if (!empty($arguments[$column_key][$delta])) {
$value = $arguments[$column_key][$delta];
}
}
else {
$value = $arguments[$column_key];
}
if ($value) {
if (isset($field_info['columns'][$column_key])) {
// Store the data in a seperate column.
$result[$column_key] = $value;
}
else {
// Add the data to the 'data' column.
$data[$column_key] = $value;
}
}
}
// Store all the other data as a serialized array in the data field.
if (!empty($data)) {
$result['data'] = serialize($data);
}
return $result;
}
}

View File

@@ -34,6 +34,33 @@ function addressfield_views_api() {
);
}
/**
* Implements hook_module_implements_alter().
*
* Moves the hook_token_info_alter() implementation to the bottom so it is
* invoked after all modules implementing the same hook.
*/
function addressfield_module_implements_alter(&$implementations, $hook) {
if ($hook == 'token_info_alter') {
// Make sure that the $implementations list is populated before altering it,
// to work around a crash experienced by some people (#2181001).
if (isset($implementations['addressfield'])) {
$group = $implementations['addressfield'];
unset($implementations['addressfield']);
$implementations['addressfield'] = $group;
}
}
}
/**
* Returns TRUE if a field map array value represents an addressfield.
*
* Provided for use as a callback by array_filter().
*/
function addressfield_field_map_filter($field) {
return !empty($field['type']) && $field['type'] == 'addressfield';
}
/**
* Get the list of format plugins.
*/
@@ -119,7 +146,10 @@ function addressfield_generate($address, array $handlers, array $context = array
ctools_include('plugins');
$format = array();
$format['#handlers'] = $handlers;
// Add the handlers, ordered by weight.
$plugins = addressfield_format_plugins();
$format['#handlers'] = array_intersect(array_keys($plugins), $handlers);
foreach ($format['#handlers'] as $handler) {
if ($callback = ctools_plugin_load_function('addressfield', 'format', $handler, 'format callback')) {
$callback($format, $address, $context);
@@ -133,7 +163,6 @@ function addressfield_generate($address, array $handlers, array $context = array
if ($context['mode'] == 'form') {
$format['#addressfield'] = TRUE;
$format['#process'][] = 'addressfield_process_format_form';
$format['#required'] = FALSE;
}
elseif ($context['mode'] == 'render') {
$format['#pre_render'][] = 'addressfield_render_address';
@@ -152,39 +181,43 @@ function addressfield_process_format_form($format, &$form_state, $complete_form)
ctools_plugin_load_function('addressfield', 'format', $handler, 'format callback');
}
_addressfield_process_format_form($format, $format['#address'], $format['#required']);
_addressfield_process_format_form($format, $format['#address']);
return $format;
}
function _addressfield_process_format_form(&$format, $address, $required) {
function _addressfield_process_format_form(&$format, $address) {
foreach (element_children($format) as $key) {
$child = &$format[$key];
// Automatically expand elements that matches one of the field of the
// address structure.
// Automatically convert any element in the format array to an appropriate
// form element that matches one of the address component names.
if (in_array($key, array('name_line', 'first_name', 'last_name', 'organisation_name', 'country', 'administrative_area', 'sub_administrative_area', 'locality', 'dependent_locality', 'postal_code', 'thoroughfare', 'premise', 'sub_premise'))) {
// Set the type.
// Set the form element type for the address component to whatever the
// address format specified in its #widget_type property.
if (isset($child['#widget_type'])) {
$child['#type'] = $child['#widget_type'];
}
else {
// If the element didn't specify a #widget_type and has options, turn it
// into a select list and unset its #size value, which is typically used
// to provide the width of a textfield.
if (isset($child['#options'])) {
$child['#type'] = 'select';
$child['#size'] = 0;
unset($child['#size']);
}
else {
// Otherwise go ahead and make it a textfield.
$child['#type'] = 'textfield';
}
}
if (!$required) {
unset($child['#required']);
}
$child['#default_value'] = $address[$key];
if (isset($address[$key])) {
$child['#default_value'] = $address[$key];
}
}
// Recurse through the child.
_addressfield_process_format_form($child, $address, $required);
// Recurse through the element's children if it has any.
_addressfield_process_format_form($child, $address);
}
}
@@ -200,8 +233,8 @@ function _addressfield_render_address(&$format, $address) {
foreach (element_children($format) as $key) {
$child = &$format[$key];
// Automatically expand elements that matches one of the field of the
// address structure.
// Automatically expand elements that match one of the fields of the address
// structure.
if (in_array($key, array('name_line', 'first_name', 'last_name', 'organisation_name', 'country', 'administrative_area', 'sub_administrative_area', 'locality', 'dependent_locality', 'postal_code', 'thoroughfare', 'premise', 'sub_premise'), TRUE)) {
if (isset($child['#render_type'])) {
$child['#type'] = $child['#render_type'];
@@ -216,12 +249,15 @@ function _addressfield_render_address(&$format, $address) {
// If the element instructs us to render the option value instead of the
// raw address element value and its #options array has a matching key,
// swap it out for the option value now.
if (!empty($child['#render_option_value']) && isset($child['#options'][$address[$key]])) {
if (!empty($child['#render_option_value']) && isset($address[$key]) && isset($child['#options'][$address[$key]])) {
$child['#children'] = check_plain($child['#options'][$address[$key]]);
}
else {
elseif (isset($address[$key])) {
$child['#children'] = check_plain($address[$key]);
}
else {
$child['#children'] = '';
}
// Skip empty elements.
if ((string) $child['#children'] === '') {
@@ -261,8 +297,12 @@ function addressfield_theme() {
*/
function theme_addressfield_container($variables) {
$element = $variables['element'];
$element['#children'] = trim($element['#children']);
// Remove the autocomplete attributes because the W3C validator complains.
// They are only used on forms anyway.
unset($element['#attributes']['autocomplete']);
unset($element['#attributes']['x-autocompletetype']);
if (strlen($element['#children']) > 0) {
$output = '<' . $element['#tag'] . drupal_attributes($element['#attributes']) . '>';
$output .= $element['#children'];
@@ -321,22 +361,27 @@ function addressfield_field_info() {
/**
* Returns an array of default values for the addressfield form elements.
*
* @param $field
* The field array.
* @param $instance
* The instance array.
* @param $address
* The current address values, if known. Allows for per-country defaults.
*
* @return
* An array of default values.
*/
function addressfield_default_values($available_countries = NULL) {
if (!isset($available_countries)) {
$available_countries = _addressfield_country_options_list();
}
// Use the default country of the site if possible.
$default_country = variable_get('site_default_country', NULL);
// If the default country is undefined or not in the list of available countries,
// just fallback to the first country in the list.
if (!$default_country || !isset($available_countries[$default_country])) {
function addressfield_default_values($field, $instance, array $address = array()) {
$available_countries = _addressfield_country_options_list($field, $instance);
$default_country = $instance['widget']['settings']['default_country'];
// If the default country is not in the list of available countries,
// fallback to the first country in the list.
if ($default_country && !isset($available_countries[$default_country])) {
$default_country = key($available_countries);
}
return array(
$default_values = array(
'country' => $default_country,
'name_line' => '',
'first_name' => '',
@@ -352,6 +397,16 @@ function addressfield_default_values($available_countries = NULL) {
'sub_premise' => '',
'data' => '',
);
// Allow other modules to alter the default values.
$context = array(
'field' => $field,
'instance' => $instance,
'address' => $address,
);
drupal_alter('addressfield_default_values', $default_values, $context);
return $default_values;
}
/**
@@ -363,6 +418,35 @@ function addressfield_field_is_empty($item, $field) {
return empty($item['country']);
}
/**
* Implements hook_field_presave().
*/
function addressfield_field_presave($entity_type, $entity, $field, $instance, $langcode, &$items) {
foreach ($items as $delta => &$item) {
// If the first name and last name are set but the name line isn't...
if (isset($item['first_name']) && isset($item['last_name']) && !isset($item['name_line'])) {
// Combine the first and last name to be the name line.
$items[$delta]['name_line'] = $items[$delta]['first_name'] . ' ' . $items[$delta]['last_name'];
}
elseif (isset($item['name_line'])) {
// Otherwise if the name line is set, separate it out into a best guess at
// the first and last name.
$names = explode(' ', $item['name_line']);
$item['first_name'] = array_shift($names);
$item['last_name'] = implode(' ', $names);
}
// Trim whitespace from all of the address components and convert any double
// spaces to single spaces.
foreach ($item as $key => &$value) {
if (!in_array($key, array('data')) && is_string($value)) {
$value = trim(str_replace(' ', ' ', $value));
}
}
}
}
/**
* Implements hook_field_widget_info()
*/
@@ -374,6 +458,7 @@ function addressfield_field_widget_info() {
'field types' => array('addressfield'),
'settings' => array(
'available_countries' => array(),
'default_country' => '',
'format_handlers' => array('address'),
),
);
@@ -399,7 +484,13 @@ function addressfield_field_widget_settings_form($field, $instance) {
'#options' => _addressfield_country_options_list(),
'#default_value' => $settings['available_countries'],
);
$form['default_country'] = array(
'#type' => 'select',
'#title' => t('Default country'),
'#options' => _addressfield_country_options_list(),
'#default_value' => $settings['default_country'],
'#empty_value' => '',
);
$form['format_handlers'] = array(
'#type' => 'checkboxes',
'#title' => t('Format handlers'),
@@ -411,41 +502,38 @@ function addressfield_field_widget_settings_form($field, $instance) {
return $form;
}
/**
* Implements hook_form_BASE_FORM_ID_alter().
*
* Removes the default values form from the field settings page.
* Allows the module to implement its own, more predictable default value
* handling, getting around #1253820 and other bugs.
*/
function addressfield_form_field_ui_field_edit_form_alter(&$form, $form_state) {
if ($form['#field']['type'] == 'addressfield') {
$form['instance']['default_value_widget']['#access'] = FALSE;
}
}
/**
* Implements hook_field_widget_form()
*/
function addressfield_field_widget_form(&$form, &$form_state, $field, $instance, $langcode, $items, $delta, $element) {
$settings = $instance['widget']['settings'];
// Generate a specific key used to identify this element to restore a default
// value upon AJAX submission regardless of where this element is in the
// $form array.
$element_key = implode('|', array($element['#entity_type'], $element['#bundle'], $element['#field_name'], $element['#language'], $element['#delta']));
// Store the key in the element array as a value so it can be easily retrieved
// in context in the $form_state['values'] array in the element validator.
$element['element_key'] = array(
'#type' => 'value',
'#value' => $element_key,
);
// Get the default address used to build the widget form elements, looking
// first in the form state, then in the stored value for the field, and then
// in the default values of the instance.
$address = array();
if (!empty($form_state['addressfield'][$element_key])) {
// Use the value from the form_state if available.
$address = $form_state['addressfield'][$element_key];
// If the form has been rebuilt via AJAX, use the form state values.
// $form_state['values'] is empty because of #limit_validation_errors, so
// $form_state['input'] needs to be used instead.
$parents = array_merge($element['#field_parents'], array($element['#field_name'], $langcode, $delta));
$input_address = drupal_array_get_nested_value($form_state['input'], $parents);
if (!empty($input_address)) {
$address = $input_address;
}
elseif (!empty($items[$delta]['country'])) {
// Else use the saved value for the field.
$address = $items[$delta];
}
else {
// Otherwise use the instance default.
$address = (array) $instance['default_value'][0];
}
// Determine the list of available countries, and if the currently selected
// country is not in it, unset it so it can be reset to the default country.
@@ -454,8 +542,8 @@ function addressfield_field_widget_form(&$form, &$form_state, $field, $instance,
unset($address['country']);
}
// Merge in default values to provide a value for every expected array key.
$address += addressfield_default_values($countries);
// Merge in default values.
$address += addressfield_default_values($field, $instance, $address);
// Add the form elements for the standard widget, which includes a country
// select list at the top that reloads the available address elements when the
@@ -466,6 +554,19 @@ function addressfield_field_widget_form(&$form, &$form_state, $field, $instance,
// in that context, and it is overridable if necessary.
$element['#type'] = 'fieldset';
if (!empty($instance['description'])) {
// Checkout panes convert the fieldset into a container, causing
// #description to not be rendered. Hence, a real element is added and
// the old #description is removed.
$element['#description'] = '';
$element['element_description'] = array(
'#markup' => $instance['description'],
'#prefix' => '<div class="fieldset-description">',
'#suffix' => '</div>',
'#weight' => -999,
);
}
// Generate the address form.
$context = array(
'mode' => 'form',
@@ -476,32 +577,39 @@ function addressfield_field_widget_form(&$form, &$form_state, $field, $instance,
);
$element += addressfield_generate($address, $settings['format_handlers'], $context);
// Mark the form element as required if necessary.
$element['#required'] = $delta == 0 && $instance['required'];
// Remove any already saved default value.
// See addressfield_form_field_ui_field_edit_form_alter() for the reasoning.
if ($form_state['build_info']['form_id'] == 'field_ui_field_edit_form') {
$element['#address'] = array('country' => '');
}
}
return $element;
}
/**
* Element validate callback: rebuilds the form on country change and stores the
* current address value in the $form_state for retrieval on rebuild.
* Element validate callback: rebuilds the form on country change.
*/
function addressfield_standard_country_validate($element, &$form_state) {
// If the country was changed, rebuild the form.
if ($element['#default_value'] != $element['#value']) {
$parents = $element['#parents'];
array_pop($parents);
$address = drupal_array_get_nested_value($form_state['values'], $parents);
// Clear the country-specific field values.
$country_specific_data = array(
'dependent_locality' => '',
'locality' => '',
'administrative_area' => '',
'postal_code' => '',
);
$address = array_diff_key($address, $country_specific_data);
drupal_array_set_nested_value($form_state['values'], $parents, $address);
drupal_array_set_nested_value($form_state['input'], $parents, $address);
$form_state['rebuild'] = TRUE;
}
$parents = $element['#parents'];
array_pop($parents);
// Search through the form values to find the current address.
$address = drupal_array_get_nested_value($form_state['values'], $parents);
// Store the present address values in the form state for retrieval by the
// widget form regardless of where the widget sits in the $form array.
$form_state['addressfield'][$address['element_key']] = array_diff_key($address, array('element_key' => ''));
}
/**
@@ -531,6 +639,9 @@ function addressfield_standard_widget_refresh($form, $form_state) {
// new country select list.
$commands[] = ajax_command_replace(NULL, render($element));
$commands[] = ajax_command_invoke('#' . $element['country']['#id'], 'focus');
// Add the status messages inside the new addressfield's wrapper element,
// just like core does.
$commands[] = ajax_command_prepend(NULL, theme('status_messages'));
// Allow other modules to add arbitrary AJAX commands on the refresh.
drupal_alter('addressfield_standard_widget_refresh', $commands, $form, $form_state);
@@ -679,12 +790,8 @@ function addressfield_property_info_callback(&$info, $entity_type, $field, $inst
*
* @see addressfield_property_info_callback()
*/
function addressfield_auto_creation() {
// We can't call addressfield_default_values() directly, because it has an
// optional array argument that will receive an invalid value when Entity API
// tries to call it directly with its usual $property_name and $context
// arguments.
return addressfield_default_values();
function addressfield_auto_creation($property_name, $context) {
return addressfield_default_values($context['field'], $context['instance']);
}
/**
@@ -730,6 +837,9 @@ function addressfield_data_property_info($name = NULL) {
'premise' => array(
'label' => t('Premise (i.e. Apartment / Suite number)'),
),
'sub_premise' => array(
'label' => t('Sub Premise (i.e. Suite, Apartment, Floor, Unknown.'),
),
);
// Add the default values for each of the address field properties.
@@ -746,13 +856,16 @@ function addressfield_data_property_info($name = NULL) {
}
/**
* Wraps country_get_list() for use as an Entity API options list.
* Returns the country list in a format suitable for use as an options list.
*/
function _addressfield_country_options_list($field = NULL, $instance = NULL) {
// Necessary for country_get_list().
require_once DRUPAL_ROOT . '/includes/locale.inc';
$countries = country_get_list();
if (module_exists('countries')) {
$countries = countries_get_countries('name', array('enabled' => COUNTRIES_ENABLED));
}
else {
require_once DRUPAL_ROOT . '/includes/locale.inc';
$countries = country_get_list();
}
if (isset($field)) {
// If the instance is not specified, loop against all the instances of the field.
@@ -771,10 +884,6 @@ function _addressfield_country_options_list($field = NULL, $instance = NULL) {
foreach ($instances as $instance) {
if (!empty($instance['widget']['settings']['available_countries'])) {
$countries = array_intersect_key($countries, $instance['widget']['settings']['available_countries']);
}
else {
// This instance allow all the countries.
$countries = country_get_list();
break;
}
}

View File

@@ -0,0 +1,233 @@
<?php
/**
* @file
* Token module integration.
*/
/**
* Implements hook_token_info().
*/
function addressfield_token_info() {
$type = array(
'name' => t('Address field'),
'description' => t('Tokens related to address field values and their components.'),
'needs-data' => 'address-field',
'field' => TRUE,
);
// Define tokens for the various components of addresses supported through the
// user interface along with two helper tokens for country and administrative
// area to distinguish between names and abbreviations.
$info['country'] = array(
'name' => t('Country name'),
'description' => t('The full name of the country.'),
);
$info['country-code'] = array(
'name' => t('Country code'),
'description' => t('The two letter ISO country code.'),
);
$info['administrative-area'] = array(
'name' => t('Administrative area (i.e. State/Province)'),
'description' => t('The administrative area value, expanded to the full name if applicable.'),
);
$info['administrative-area-raw'] = array(
'name' => t('Administrative area (raw value)'),
'description' => t('The raw administrative area value.'),
);
$info['locality'] = array(
'name' => t('Locality (i.e. City)'),
'description' => t('The locality value.'),
);
$info['postal-code'] = array(
'name' => t('Postal code'),
'description' => t('The postal code value.'),
);
$info['thoroughfare'] = array(
'name' => t('Thoroughfare (i.e. Street address)'),
'description' => t('The thoroughfare value.'),
);
$info['premise'] = array(
'name' => t('Premise (i.e. Street address)'),
'description' => t('The premise value.'),
);
$info['sub_premise'] = array(
'name' => t('Sub Premise (i.e. Suite, Apartment, Floor, Unknown.)'),
'description' => t('The sub premise value.'),
);
$info['organisation'] = array(
'name' => t('Organisation'),
'description' => t('The organisation name value.'),
);
$info['name-line'] = array(
'name' => t('Full name'),
'description' => t('The name line value of the address.'),
);
$info['first-name'] = array(
'name' => t('First name'),
'description' => t('The first name value.'),
);
$info['last-name'] = array(
'name' => t('Last name'),
'description' => t('The last name value.'),
);
// Add a helper token to format addresses as expected by MailChimp.
$info['format-mailchimp'] = array(
'name' => t('Address formatted for MailChimp'),
'description' => t('The full address formatted for import into MailChimp.'),
);
return array(
'types' => array('address-field' => $type),
'tokens' => array('address-field' => $info),
);
}
/**
* Implements hook_token_info_alter().
*/
function addressfield_token_info_alter(&$data) {
// Loop over every address field on the site.
foreach (array_filter(field_info_field_map(), 'addressfield_field_map_filter') as $field_name => $field) {
foreach ($data['tokens'] as $group => $token){
if (isset($data['tokens'][$group][$field_name]) && is_array($data['tokens'][$group][$field_name])) {
// Set the token type for the field to use the addressfield child tokens.
$data['tokens'][$group][$field_name]['type'] = 'address-field';
}
}
}
}
/**
* Implements hook_tokens().
*/
function addressfield_tokens($type, $tokens, array $data = array(), array $options = array()) {
if (isset($options['language'])) {
$language_code = $options['language']->language;
}
else {
$language_code = LANGUAGE_NONE;
}
$sanitize = !empty($options['sanitize']);
$replacements = array();
// If we're generating tokens for an address field, extract the address data
// from the field value array and generate the necessary replacements.
if ($type == 'address-field' && !empty($data['address-field'][$language_code]) && is_array($data['address-field'][$language_code])) {
$address = reset($data['address-field'][$language_code]);
foreach ($tokens as $name => $original) {
switch ($name) {
case 'country':
$countries = _addressfield_country_options_list();
$replacements[$original] = $sanitize ? check_plain($countries[$address['country']]) : $countries[$address['country']];
break;
case 'country-code':
$replacements[$original] = $sanitize ? check_plain($address['country']) : $address['country'];
break;
case 'administrative-area':
// If we received format handlers in the data array, generate the form
// for the address field to see if the administrative area should be
// expanded from an abbreviation to a related name.
$administrative_area = $address['administrative_area'];
if (!empty($data['format_handlers'])) {
$form = addressfield_generate($address, $data['format_handlers'], array('mode' => 'form'));
if (!empty($form['locality_block']['administrative_area']['#options'][$administrative_area])) {
$administrative_area = $form['locality_block']['administrative_area']['#options'][$administrative_area];
}
}
$replacements[$original] = $sanitize ? check_plain($administrative_area) : $administrative_area;
break;
case 'administrative-area-raw':
$replacements[$original] = $sanitize ? check_plain($address['administrative_area']) : $address['administrative_area'];
break;
case 'locality':
$replacements[$original] = $sanitize ? check_plain($address['locality']) : $address['locality'];
break;
case 'postal-code':
$replacements[$original] = $sanitize ? check_plain($address['postal_code']) : $address['postal_code'];
break;
case 'thoroughfare':
$replacements[$original] = $sanitize ? check_plain($address['thoroughfare']) : $address['thoroughfare'];
break;
case 'premise':
$replacements[$original] = $sanitize ? check_plain($address['premise']) : $address['premise'];
break;
case 'sub_premise':
$replacements[$original] = $sanitize ? check_plain($address['sub_premise']) : $address['sub_premise'];
break;
case 'organisation':
$replacements[$original] = $sanitize ? check_plain($address['organisation_name']) : $address['organisation_name'];
break;
case 'name-line':
$replacements[$original] = $sanitize ? check_plain($address['name_line']) : $address['name_line'];
break;
case 'first-name':
$replacements[$original] = $sanitize ? check_plain($address['first_name']) : $address['first_name'];
break;
case 'last-name':
$replacements[$original] = $sanitize ? check_plain($address['last_name']) : $address['last_name'];
break;
// See: http://kb.mailchimp.com/article/how-do-i-format-my-list-fields-to-import-them
case 'format-mailchimp':
$components = array();
foreach (array('thoroughfare', 'premise', 'locality', 'administrative_area', 'postal_code', 'country') as $component) {
if (!empty($address[$component])) {
$components[] = $address[$component];
}
}
$format_mailchimp = implode(' ', $components);
$replacements[$original] = $sanitize ? check_plain($format_mailchimp) : $format_mailchimp;
break;
}
}
}
// The Token module extends direct token generation by using a generic entity
// token generation process. Since we intend to overwrite the default Token
// module implementation of address field tokens, we use this generic token
// generation process to find and replace address field tokens on relevant
// entities. This ensures our tokens aren't overwritten by the Token module
// and helps us avoid having to do the entity detection ourselves.
if ($type == 'entity') {
// Loop over the address fields defined on the site.
foreach (array_filter(field_info_field_map(), 'addressfield_field_map_filter') as $field_name => $field) {
// If there are any address field tokens in the token list...
if ($addressfield_tokens = token_find_with_prefix($tokens, $field_name)) {
// If the current field is on the matching entity type...
if (!empty($field['bundles'][$data['entity_type']])) {
// Extract the format handlers selected in a representative instance
// settings form for use in formatting tokens.
$instance = field_info_instance($data['entity_type'], $field_name, reset($field['bundles'][$data['entity_type']]));
$format_handlers = $instance['widget']['settings']['format_handlers'];
}
// Generate the necessary address field tokens for the entity.
$replacements += token_generate('address-field', $addressfield_tokens, array('address-field' => $data['entity']->$field_name, 'format_handlers' => $format_handlers), $options);
}
}
}
return $replacements;
}

View File

@@ -7,9 +7,9 @@ hidden = TRUE
dependencies[] = ctools
dependencies[] = addressfield
; Information added by drupal.org packaging script on 2013-05-07
version = "7.x-1.0-beta4"
; Information added by Drupal.org packaging script on 2015-01-16
version = "7.x-1.0"
core = "7.x"
project = "addressfield"
datestamp = "1367945112"
datestamp = "1421426885"

View File

@@ -18,10 +18,9 @@ $plugin = array(
* @see CALLBACK_addressfield_format_callback()
*/
function addressfield_format_address_hide_country(&$format, $address, $context = array()) {
// When building the format for a form, we expect the country element to have
// an #options list. If it does, and there is only one option, hide the field
// by setting #access to FALSE.
if ($context['mode'] == 'form') {
// Hide the country element only if the whole field is required, otherwise
// there will always be an additional None option.
if ($context['mode'] == 'form' && $context['instance']['required']) {
if (!empty($format['country']['#options']) && count($format['country']['#options']) == 1) {
$format['country']['#access'] = FALSE;
}

View File

@@ -0,0 +1,24 @@
<?php
/**
* @file
* Hide the postal code field.
*/
$plugin = array(
'title' => t('Hide the postal code'),
'format callback' => 'addressfield_format_address_hide_postal_code',
'type' => 'address',
'weight' => -85,
);
/**
* Format callback.
*
* @see CALLBACK_addressfield_format_callback()
*/
function addressfield_format_address_hide_postal_code(&$format, $address, $context = array()) {
if (isset($format['locality_block']['postal_code'])) {
$format['locality_block']['postal_code']['#access'] = FALSE;
}
}

View File

@@ -0,0 +1,24 @@
<?php
/**
* @file
* Hide the street address fields.
*/
$plugin = array(
'title' => t('Hide the street address'),
'format callback' => 'addressfield_format_address_hide_street',
'type' => 'address',
'weight' => -85,
);
/**
* Format callback.
*
* @see CALLBACK_addressfield_format_callback()
*/
function addressfield_format_address_hide_street(&$format, $address, $context = array()) {
if (isset($format['street_block'])) {
$format['street_block']['#access'] = FALSE;
}
}

View File

@@ -0,0 +1,36 @@
<?php
/**
* @file
* Make all fields optional.
* Allows users to save incomplete addresses, bypassing validation.
*/
$plugin = array(
'title' => t('Make all fields optional (Not recommended)'),
'format callback' => 'addressfield_format_address_optional',
'type' => 'address',
'weight' => 100,
);
/**
* Format callback.
*
* @see CALLBACK_addressfield_format_callback()
*/
function addressfield_format_address_optional(&$format, $address, $context = array()) {
if (isset($format['name_block'])) {
if (isset($format['name_block']['name_line'])) {
$format['name_block']['name_line']['#required'] = FALSE;
}
elseif (isset($format['name_block']['first_name'])) {
$format['name_block']['first_name']['#required'] = FALSE;
$format['name_block']['last_name']['#required'] = FALSE;
}
}
$format['street_block']['thoroughfare']['#required'] = FALSE;
$format['locality_block']['postal_code']['#required'] = FALSE;
$format['locality_block']['dependent_locality']['#required'] = FALSE;
$format['locality_block']['locality']['#required'] = FALSE;
$format['locality_block']['administrative_area']['#required'] = FALSE;
}

View File

@@ -18,370 +18,222 @@ $plugin = array(
* @see CALLBACK_addressfield_format_callback()
*/
function addressfield_format_address_generate(&$format, $address, $context = array()) {
// We start with a reasonable default: a simple block format suitable
// for international shipping. We extend it with country-specific heuristics
// below.
// Load the predefined address format for the selected country.
module_load_include('inc', 'addressfield', 'addressfield.address_formats');
$address_format = addressfield_get_address_format($address['country']);
// Used to move certain fields to their own row.
$clearfix = '<div class="clearfix"></div>';
// The street block.
$format['street_block'] = array(
'#type' => 'addressfield_container',
'#attributes' => array('class' => array('street-block')),
'#attributes' => array(
'class' => array('street-block'),
),
'#weight' => 0,
);
$format['street_block']['thoroughfare'] = array(
'#title' => t('Address 1'),
'#tag' => 'div',
'#attributes' => array('class' => array('thoroughfare')),
'#attributes' => array(
'class' => array('thoroughfare'),
'x-autocompletetype' => 'address-line1',
'autocomplete' => 'address-line1',
),
'#size' => 30,
// The #required will be automatically set to FALSE when processing.
'#required' => TRUE,
);
$format['street_block']['premise'] = array(
'#title' => t('Address 2'),
'#tag' => 'div',
'#attributes' => array('class' => array('premise')),
'#attributes' => array(
'class' => array('premise'),
'x-autocompletetype' => 'address-line2',
'autocomplete' => 'address-line2',
),
'#size' => 30,
);
$format['locality_block'] = array(
'#type' => 'addressfield_container',
'#attributes' => array('class' => array('addressfield-container-inline', 'locality-block', 'country-' . $address['country'])),
'#attributes' => array(
'class' => array('addressfield-container-inline', 'locality-block', 'country-' . $address['country']),
),
'#weight' => 50,
);
$format['locality_block']['#attached']['css'][] = drupal_get_path('module', 'addressfield') . '/addressfield.css';
$format['locality_block']['postal_code'] = array(
'#title' => t('Postal code'),
'#title' => $address_format['postal_code_label'],
'#required' => in_array('postal_code', $address_format['required_fields']),
'#access' => in_array('postal_code', $address_format['used_fields']),
'#size' => 10,
'#required' => TRUE,
'#attributes' => array('class' => array('postal-code')),
'#attributes' => array(
'class' => array('postal-code'),
'x-autocompletetype' => 'postal-code',
'autocomplete' => 'postal-code',
),
);
$format['locality_block']['dependent_locality'] = array(
'#title' => $address_format['dependent_locality_label'],
'#required' => in_array('dependent_locality', $address_format['required_fields']),
'#access' => in_array('dependent_locality', $address_format['used_fields']),
'#size' => 25,
'#tag' => 'div',
'#attributes' => array(
'class' => array('dependent-locality')
),
// Most formats place this field in its own row.
'#suffix' => $clearfix,
);
$format['locality_block']['locality'] = array(
'#title' => t('City'),
'#title' => $address_format['locality_label'],
'#required' => in_array('locality', $address_format['required_fields']),
'#access' => in_array('locality', $address_format['used_fields']),
'#size' => 30,
'#required' => TRUE,
'#prefix' => ' ',
'#attributes' => array('class' => array('locality')),
'#attributes' => array(
'class' => array('locality'),
'x-autocompletetype' => 'locality',
'autocomplete' => 'locality',
),
);
$format['locality_block']['administrative_area'] = array(
'#title' => $address_format['administrative_area_label'],
'#required' => in_array('administrative_area', $address_format['required_fields']),
'#access' => in_array('administrative_area', $address_format['used_fields']),
'#empty_value' => '',
'#size' => 10,
'#prefix' => ' ',
'#render_option_value' => $address_format['render_administrative_area_value'],
'#attributes' => array(
'class' => array('state'),
'x-autocompletetype' => 'region',
'autocomplete' => 'region',
),
);
$format['country'] = array(
'#title' => t('Country'),
'#options' => _addressfield_country_options_list(),
'#render_option_value' => TRUE,
'#required' => TRUE,
'#attributes' => array('class' => array('country')),
'#attributes' => array(
'class' => array('country'),
'x-autocompletetype' => 'country',
'autocomplete' => 'country',
),
'#weight' => 100,
);
// Those countries do not seem to have a relevant postal code.
static $countries_no_postal_code = array('AF', 'AG', 'AL', 'AO', 'BB', 'BI', 'BJ', 'BO', 'BS', 'BW', 'BZ', 'CF', 'CG', 'CM', 'CO', 'DJ', 'DM', 'EG', 'ER', 'FJ', 'GD', 'GH', 'GM', 'GQ', 'GY', 'HK', 'IE', 'KI', 'KM', 'KP', 'KY', 'LC', 'LY', 'ML', 'MR', 'NA', 'NR', 'RW', 'SB', 'SC', 'SL', 'SR', 'ST', 'TD', 'TG', 'TL', 'TO', 'TT', 'TV', 'TZ', 'UG', 'VC', 'VU', 'WS', 'ZW');
if (in_array($address['country'], $countries_no_postal_code)) {
unset($format['locality_block']['postal_code']);
if (empty($format['locality_block']['postal_code']['#access'])) {
// Remove the prefix from the first widget of the block.
$element_children = element_children($format['locality_block']);
$first_child = reset($element_children);
unset($format['locality_block'][$first_child]['#prefix']);
}
// Those countries generally use the administrative area in postal addresses.
static $countries_administrative_area = array('AR', 'AU', 'BR', 'BS', 'BY', 'BZ', 'CA', 'CN', 'DO', 'EG', 'ES', 'FJ', 'FM', 'GB', 'HN', 'ID', 'IE', 'IN', 'IT', 'JO', 'JP', 'KI', 'KN', 'KR', 'KW', 'KY', 'KZ', 'MX', 'MY', 'MZ', 'NG', 'NI', 'NR', 'NZ', 'OM', 'PA', 'PF', 'PG', 'PH', 'PR', 'PW', 'RU', 'SM', 'SO', 'SR', 'SV', 'TH', 'TW', 'UA', 'US', 'UY', 'VE', 'VI', 'VN', 'YU', 'ZA');
if (in_array($address['country'], $countries_administrative_area)) {
$format['locality_block']['administrative_area'] = array(
'#title' => t('State', array(), array('context' => 'addressfield')),
'#size' => 10,
'#required' => TRUE,
'#prefix' => ' ',
'#attributes' => array('class' => array('state')),
);
if (!empty($format['locality_block']['administrative_area']['#access'])) {
// Set the predefined administrative areas, if found.
module_load_include('inc', 'addressfield', 'addressfield.administrative_areas');
$administrative_areas = addressfield_get_administrative_areas($address['country']);
$format['locality_block']['administrative_area']['#options'] = $administrative_areas;
}
// A few countries have a well-known list of administrative divisions.
if ($address['country'] == 'US') {
$format['locality_block']['administrative_area']['#options'] = array(
'' => t('--'),
'AL' => t('Alabama'),
'AK' => t('Alaska'),
'AZ' => t('Arizona'),
'AR' => t('Arkansas'),
'CA' => t('California'),
'CO' => t('Colorado'),
'CT' => t('Connecticut'),
'DE' => t('Delaware'),
'DC' => t('District Of Columbia'),
'FL' => t('Florida'),
'GA' => t('Georgia'),
'HI' => t('Hawaii'),
'ID' => t('Idaho'),
'IL' => t('Illinois'),
'IN' => t('Indiana'),
'IA' => t('Iowa'),
'KS' => t('Kansas'),
'KY' => t('Kentucky'),
'LA' => t('Louisiana'),
'ME' => t('Maine'),
'MD' => t('Maryland'),
'MA' => t('Massachusetts'),
'MI' => t('Michigan'),
'MN' => t('Minnesota'),
'MS' => t('Mississippi'),
'MO' => t('Missouri'),
'MT' => t('Montana'),
'NE' => t('Nebraska'),
'NV' => t('Nevada'),
'NH' => t('New Hampshire'),
'NJ' => t('New Jersey'),
'NM' => t('New Mexico'),
'NY' => t('New York'),
'NC' => t('North Carolina'),
'ND' => t('North Dakota'),
'OH' => t('Ohio'),
'OK' => t('Oklahoma'),
'OR' => t('Oregon'),
'PA' => t('Pennsylvania'),
'RI' => t('Rhode Island'),
'SC' => t('South Carolina'),
'SD' => t('South Dakota'),
'TN' => t('Tennessee'),
'TX' => t('Texas'),
'UT' => t('Utah'),
'VT' => t('Vermont'),
'VA' => t('Virginia'),
'WA' => t('Washington'),
'WV' => t('West Virginia'),
'WI' => t('Wisconsin'),
'WY' => t('Wyoming'),
' ' => t('--'),
'AA' => t('Armed Forces (Americas)'),
'AE' => t('Armed Forces (Europe, Canada, Middle East, Africa)'),
'AP' => t('Armed Forces (Pacific)'),
'AS' => t('American Samoa'),
'FM' => t('Federated States of Micronesia'),
'GU' => t('Guam'),
'MH' => t('Marshall Islands'),
'MP' => t('Northern Mariana Islands'),
'PW' => t('Palau'),
'PR' => t('Puerto Rico'),
'VI' => t('Virgin Islands'),
);
$format['locality_block']['postal_code']['#title'] = t('ZIP Code');
// Country-specific customizations.
if (in_array($address['country'], array('AU', 'EE', 'LT', 'LV', 'NZ', 'RU'))) {
// These countries don't use the "Address 2" line.
// Leave it as a precaution, but hide the label to avoid confusing users.
$format['street_block']['thoroughfare']['#title'] = t('Address');
$format['street_block']['premise']['#title_display'] = 'invisible';
}
elseif ($address['country'] == 'US') {
if ($context['mode'] == 'render') {
$format['locality_block']['locality']['#suffix'] = ',';
}
}
else if ($address['country'] == 'IT') {
$format['locality_block']['administrative_area']['#options'] = array(
'' => t('--'),
'AG' => t('Agrigento'),
'AL' => t('Alessandria'),
'AN' => t('Ancona'),
'AO' => t("Valle d'Aosta/Vallée d'Aoste"),
'AP' => t('Ascoli Piceno'),
'AQ' => t("L'Aquila"),
'AR' => t('Arezzo'),
'AT' => t('Asti'),
'AV' => t('Avellino'),
'BA' => t('Bari'),
'BG' => t('Bergamo'),
'BI' => t('Biella'),
'BL' => t('Belluno'),
'BN' => t('Benevento'),
'BO' => t('Bologna'),
'BR' => t('Brindisi'),
'BS' => t('Brescia'),
'BT' => t('Barletta-Andria-Trani'),
'BZ' => t('Bolzano/Bozen'),
'CA' => t('Cagliari'),
'CB' => t('Campobasso'),
'CE' => t('Caserta'),
'CH' => t('Chieti'),
'CI' => t('Carbonia-Iglesias'),
'CL' => t('Caltanissetta'),
'CN' => t('Cuneo'),
'CO' => t('Como'),
'CR' => t('Cremona'),
'CS' => t('Cosenza'),
'CT' => t('Catania'),
'CZ' => t('Catanzaro'),
'EN' => t('Enna'),
'FC' => t('Forlì-Cesena'),
'FE' => t('Ferrara'),
'FG' => t('Foggia'),
'FI' => t('Firenze'),
'FM' => t('Fermo'),
'FR' => t('Frosinone'),
'GE' => t('Genova'),
'GO' => t('Gorizia'),
'GR' => t('Grosseto'),
'IM' => t('Imperia'),
'IS' => t('Isernia'),
'KR' => t('Crotone'),
'LC' => t('Lecco'),
'LE' => t('Lecce'),
'LI' => t('Livorno'),
'LO' => t('Lodi'),
'LT' => t('Latina'),
'LU' => t('Lucca'),
'MB' => t('Monza e Brianza'),
'MC' => t('Macerata'),
'ME' => t('Messina'),
'MI' => t('Milano'),
'MN' => t('Mantova'),
'MO' => t('Modena'),
'MS' => t('Massa-Carrara'),
'MT' => t('Matera'),
'NA' => t('Napoli'),
'NO' => t('Novara'),
'NU' => t('Nuoro'),
'OG' => t('Ogliastra'),
'OR' => t('Oristano'),
'OT' => t('Olbia-Tempio'),
'PA' => t('Palermo'),
'PC' => t('Piacenza'),
'PD' => t('Padova'),
'PE' => t('Pescara'),
'PG' => t('Perugia'),
'PI' => t('Pisa'),
'PN' => t('Pordenone'),
'PO' => t('Prato'),
'PR' => t('Parma'),
'PT' => t('Pistoia'),
'PU' => t('Pesaro e Urbino'),
'PV' => t('Pavia'),
'PZ' => t('Potenza'),
'RA' => t('Ravenna'),
'RC' => t('Reggio di Calabria'),
'RE' => t("Reggio nell'Emilia"),
'RG' => t('Ragusa'),
'RI' => t('Rieti'),
'RM' => t('Roma'),
'RN' => t('Rimini'),
'RO' => t('Rovigo'),
'SA' => t('Salerno'),
'SI' => t('Siena'),
'SO' => t('Sondrio'),
'SP' => t('La Spezia'),
'SR' => t('Siracusa'),
'SS' => t('Sassari'),
'SV' => t('Savona'),
'TA' => t('Taranto'),
'TE' => t('Teramo'),
'TN' => t('Trento'),
'TO' => t('Torino'),
'TP' => t('Trapani'),
'TR' => t('Terni'),
'TS' => t('Trieste'),
'TV' => t('Treviso'),
'UD' => t('Udine'),
'VA' => t('Varese'),
'VB' => t('Verbano-Cusio-Ossola'),
'VC' => t('Vercelli'),
'VE' => t('Venezia'),
'VI' => t('Vicenza'),
'VR' => t('Verona'),
'VS' => t('Medio Campidano'),
'VT' => t('Viterbo'),
'VV' => t('Vibo Valentia'),
elseif ($address['country'] == 'BR') {
$format['locality_block']['dependent_locality']['#suffix'] = $clearfix;
$format['locality_block']['dependent_locality']['#tag'] = 'div';
$format['locality_block']['administrative_area']['#suffix'] = $clearfix;
$format['locality_block']['postal_code']['#tag'] = 'div';
// Change some titles to make translation easier.
$format['street_block']['#attributes'] = array(
'class' => array('addressfield-container-inline'),
);
$format['locality_block']['administrative_area']['#title'] = t('Province');
$format['street_block']['thoroughfare']['#title'] = t('Thoroughfare');
$format['street_block']['thoroughfare']['#tag'] = NULL;
$format['street_block']['premise'] = array(
'#title' => t('Complement'),
'#tag' => NULL,
'#attributes' => array('class' => array('premise')),
'#size' => 20,
'#prefix' => ', ',
);
$format['locality_block']['locality']['#suffix'] = ' - ';
// Hide suffixes and prefixes while in form.
if ($context['mode'] == 'form') {
$format['street_block']['premise']['#prefix'] = NULL;
$format['street_block']['premise']['#suffix'] = NULL;
$format['locality_block']['locality']['#suffix'] = NULL;
}
}
else if ($address['country'] == 'BR') {
$format['locality_block']['administrative_area']['#render_option_value'] = TRUE;
$format['locality_block']['administrative_area']['#options'] = array(
'' => t('--'),
'AC' => t('Acre'),
'AL' => t('Alagoas'),
'AM' => t('Amazonas'),
'AP' => t('Amapá'),
'BA' => t('Bahia'),
'CE' => t('Ceará'),
'DF' => t('Distrito Federal'),
'ES' => t('Espírito Santo'),
'GO' => t('Goiás'),
'MA' => t('Maranhão'),
'MG' => t('Minas Gerais'),
'MS' => t('Mato Grosso do Sul'),
'MT' => t('Mato Grosso'),
'PA' => t('Pará'),
'PB' => t('Paraíba'),
'PE' => t('Pernambuco'),
'PI' => t('Piauí'),
'PR' => t('Paraná'),
'RJ' => t('Rio de Janeiro'),
'RN' => t('Rio Grande do Norte'),
'RO' => t('Rondônia'),
'RR' => t('Roraima'),
'RS' => t('Rio Grande do Sul'),
'SC' => t('Santa Catarina'),
'SE' => t('Sergipe'),
'SP' => t('São Paulo'),
'TO' => t('Tocantins'),
);
elseif ($address['country'] == 'CN') {
$format['locality_block']['locality']['#suffix'] = $clearfix;
}
else if ($address['country'] == 'CA') {
$format['locality_block']['administrative_area']['#options'] = array(
'' => t('--'),
'AB' => t('Alberta'),
'BC' => t('British Columbia'),
'MB' => t('Manitoba'),
'NB' => t('New Brunswick'),
'NL' => t('Newfoundland and Labrador'),
'NT' => t('Northwest Territories'),
'NS' => t('Nova Scotia'),
'NU' => t('Nunavut'),
'ON' => t('Ontario'),
'PE' => t('Prince Edward Island'),
'QC' => t('Quebec'),
'SK' => t('Saskatchewan'),
'YT' => t('Yukon Territory'),
);
$format['locality_block']['administrative_area']['#title'] = t('Province');
elseif ($address['country'] == 'CA') {
if ($context['mode'] == 'render') {
$format['locality_block']['locality']['#suffix'] = ',';
}
}
else if ($address['country'] == 'AU') {
$format['locality_block']['administrative_area']['#options'] = array(
'' => t('--'),
'ACT' => t('Australian Capital Territory'),
'NSW' => t('New South Wales'),
'NT' => t('Northern Territory'),
'QLD' => t('Queensland'),
'SA' => t('South Australia'),
'TAS' => t('Tasmania'),
'VIC' => t('Victoria'),
'WA' => t('Western Australia'),
);
elseif ($address['country'] == 'GB') {
$format['locality_block']['administrative_area']['#size'] = '30';
}
else if ($address['country'] == 'NZ') {
$format['locality_block']['locality']['#title'] = ('Town/City');
$format['locality_block']['postal_code']['#title'] = t('Postcode');
$format['locality_block']['administrative_area']['#render_option_value'] = TRUE;
$format['locality_block']['administrative_area']['#title'] = t('Region');
$format['locality_block']['administrative_area']['#required'] = FALSE;
$format['locality_block']['administrative_area']['#options'] = array(
'' => t('--'),
'AUK' => t('Auckland'),
'BOP' => t('Bay of Plenty'),
'CAN' => t('Canterbury'),
'HKB' => t("Hawke's Bay"),
'MWT' => t('Manawatu-Wanganui'),
'NTL' => t('Northland'),
'OTA' => t('Otago'),
'STL' => t('Southland'),
'TKI' => t('Taranaki'),
'WKO' => t('Waikato'),
'WGN' => t('Wellington'),
'WTC' => t('West Coast'),
'GIS' => t('Gisborne District'),
'MBH' => t('Marlborough District'),
'NSN' => t('Nelson City'),
'TAS' => t('Tasman District'),
'CIT' => t('Chatham Islands Territory'),
);
elseif ($address['country'] == 'ID') {
$format['locality_block']['administrative_area']['#weight'] = 1;
}
elseif ($address['country'] == 'JP') {
$format['locality_block']['#weight'] = 10;
$format['locality_block']['postal_code']['#weight'] = 10;
$format['locality_block']['postal_code']['#tag'] = 'div';
$format['locality_block']['postal_code']['#size'] = 30;
$format['locality_block']['administrative_area']['#weight'] = 20;
$format['locality_block']['administrative_area']['#size'] = 30;
$format['locality_block']['locality']['#weight'] = 30;
$format['street_block']['#weight'] = 20;
}
elseif ($address['country'] == 'PE') {
$format['locality_block']['administrative_area']['#weight'] = 1;
$format['locality_block']['locality']['#weight'] = 2;
}
elseif ($address['country'] == 'PH' || $address['country'] == 'TH') {
$format['locality_block']['dependent_locality']['#suffix'] = '';
$format['locality_block']['locality']['#suffix'] = $clearfix;
}
// Those countries tend to put the postal code after the locality.
static $countries_postal_code_after_locality = array('AU', 'BD', 'BF', 'BH', 'BM', 'BN', 'BT', 'CA', 'FM', 'GB', 'ID', 'IN', 'JM', 'JO', 'KH', 'LB', 'LS', 'LV', 'MM', 'MN', 'MV', 'MW', 'NG', 'NP', 'NZ', 'PE', 'PK', 'PR', 'PW', 'SA', 'SG', 'SO', 'TH', 'US', 'VI', 'VG', 'VN');
// These countries show every field in its own row.
$countries_field_per_row = array(
'AM', 'EG', 'FK', 'GB', 'GG', 'GS', 'HK', 'HU', 'IE', 'IM', 'IO', 'JE', 'JM',
'JP', 'KE', 'KR', 'KZ', 'LK', 'PA', 'PN', 'RU', 'SC', 'SH', 'SZ', 'TC', 'UA',
'VG', 'ZA',
);
if (in_array($address['country'], $countries_field_per_row)) {
$format['locality_block']['#attributes']['class'][0] = 'addressfield-container';
$format['locality_block']['postal_code']['#prefix'] = '';
$format['locality_block']['postal_code']['#tag'] = 'div';
$format['locality_block']['locality']['#prefix'] = '';
$format['locality_block']['locality']['#tag'] = 'div';
$format['locality_block']['administrative_area']['#prefix'] = '';
$format['locality_block']['administrative_area']['#tag'] = 'div';
}
// These countries tend to put the postal code after the locality.
$countries_postal_code_after_locality = array(
'AS', 'AU', 'BD', 'BF', 'BH', 'BM', 'BN', 'BR', 'BT', 'CA', 'CC', 'CN', 'CX',
'EG', 'FK', 'FM', 'GB', 'GG', 'GS', 'GU', 'HN', 'HU', 'ID', 'IL', 'IM', 'IN',
'IO', 'IQ', 'IR', 'JE', 'JO', 'JP', 'KE', 'KH', 'KR', 'LB', 'LK', 'LS', 'LV',
'MH', 'MM', 'MN', 'MP', 'MT', 'MV', 'MX', 'MY', 'NF', 'NG', 'NP', 'NZ', 'PG',
'PH', 'PK', 'PN', 'PR', 'PW', 'RU', 'SA', 'SH', 'SO', 'SZ', 'TC', 'TH', 'TW',
'UA', 'UM', 'US', 'VE', 'VI', 'VG', 'VN', 'ZA',
);
if (in_array($address['country'], $countries_postal_code_after_locality)) {
// Take the widget out of the array.
$postal_code_widget = $format['locality_block']['postal_code'];
@@ -397,44 +249,6 @@ function addressfield_format_address_generate(&$format, $address, $context = arr
unset($format['locality_block'][$first_child]['#prefix']);
}
// GB-specific tweaks
if ($address['country'] == 'GB') {
// Locality
$format['locality_block']['locality'] = array_merge(
$format['locality_block']['locality'],
array(
'#title' => t('Town/City'),
'#weight' => 40,
'#prefix' => '',
'#tag' => 'div',
)
);
// Administrative
$format['locality_block']['administrative_area'] = array_merge(
$format['locality_block']['administrative_area'],
array(
'#title' => t('County'),
'#required' => FALSE,
'#weight' => 50,
'#size' => 30,
'#prefix' => '',
'#tag' => 'div',
)
);
// Postal code
$format['locality_block']['postal_code'] = array_merge(
$format['locality_block']['postal_code'],
array(
'#title' => t('Postcode'),
'#weight' => 60,
'#prefix' => '',
'#tag' => 'div',
)
);
}
if ($context['mode'] == 'form') {
// Provide a wrapper ID for AJAX replacement based on country selection.
if (!isset($format['#wrapper_id'])) {
@@ -442,15 +256,6 @@ function addressfield_format_address_generate(&$format, $address, $context = arr
$format['#prefix'] = '<div id="' . $format['#wrapper_id'] . '">';
$format['#suffix'] = '</div>';
}
// Form mode, move the country selector to the top of the form.
$format['country']['#weight'] = -10;
// Limit it to the countries supported by the widget.
if (isset($context['field'])) {
$format['country']['#options'] = _addressfield_country_options_list($context['field'], $context['instance']);
}
// AJAX enable it.
$format['country']['#ajax'] = array(
'callback' => 'addressfield_standard_widget_refresh',
@@ -460,12 +265,25 @@ function addressfield_format_address_generate(&$format, $address, $context = arr
// Don't validate any element when the country is changed.
$format['country']['#limit_validation_errors'] = array();
if (isset($context['delta']) && $context['delta'] > 0) {
// On subsequent elements of a field, we make the country field non
// required and add a ' - None - ' option to it, so as to allow the
// user to remove the address by clearing the country field.
// Move the country selector to the top of the form.
$format['country']['#weight'] = -500;
// Limit it to the countries supported by the widget.
if (isset($context['field'])) {
$format['country']['#options'] = _addressfield_country_options_list($context['field'], $context['instance']);
}
// The whole field is considered empty if the country column is empty.
// Therefore, if the field is optional, allow the country to be optional.
// The same logic applies if the field allows multiple values, in which case
// only the first delta needs to have a value.
if (empty($context['instance']['required']) || (isset($context['delta']) && $context['delta'] > 0)) {
$format['country']['#required'] = FALSE;
$format['country']['#empty_value'] = '';
// Hide all other fields until the country is selected.
if (empty($address['country'])) {
$format['street_block']['#access'] = FALSE;
$format['locality_block']['#access'] = FALSE;
}
}
}
}

View File

@@ -20,20 +20,33 @@ $plugin = array(
function addressfield_format_name_full_generate(&$format, $address) {
$format['name_block'] = array(
'#type' => 'addressfield_container',
'#attributes' => array('class' => array('addressfield-container-inline', 'name-block')),
'#attributes' => array(
'class' => array('addressfield-container-inline', 'name-block'),
),
'#weight' => -100,
// The addressfield is considered empty without a country, hide all fields
// until one is selected.
'#access' => !empty($address['country']),
);
$format['name_block']['first_name'] = array(
'#title' => t('First name'),
'#size' => 30,
'#required' => TRUE,
'#attributes' => array('class' => array('first-name')),
'#attributes' => array(
'class' => array('first-name'),
'x-autocompletetype' => 'given-name',
'autocomplete' => 'given-name',
),
);
$format['name_block']['last_name'] = array(
'#title' => t('Last name'),
'#size' => 30,
'#required' => TRUE,
'#prefix' => ' ',
'#attributes' => array('class' => array('last-name')),
'#attributes' => array(
'class' => array('last-name'),
'x-autocompletetype' => 'family-name',
'autocomplete' => 'family-name',
),
);
}

View File

@@ -22,11 +22,18 @@ function addressfield_format_name_oneline_generate(&$format, $address) {
'#type' => 'addressfield_container',
'#attributes' => array('class' => array('addressfield-container-inline', 'name-block')),
'#weight' => -100,
// The addressfield is considered empty without a country, hide all fields
// until one is selected.
'#access' => !empty($address['country']),
);
$format['name_block']['name_line'] = array(
'#title' => t('Full name'),
'#tag' => 'div',
'#attributes' => array('class' => array('name-block')),
'#attributes' => array(
'class' => array('name-block'),
'x-autocompletetype' => 'name',
'autocomplete' => 'name',
),
'#size' => 30,
'#required' => TRUE,
);

View File

@@ -22,10 +22,17 @@ function addressfield_format_organisation_generate(&$format, $address) {
'#type' => 'addressfield_container',
'#attributes' => array('class' => array('addressfield-container-inline', 'name-block')),
'#weight' => -50,
// The addressfield is considered empty without a country, hide all fields
// until one is selected.
'#access' => !empty($address['country']),
);
$format['organisation_block']['organisation_name'] = array(
'#title' => t('Company'),
'#size' => 30,
'#attributes' => array('class' => array('organisation-name')),
'#attributes' => array(
'class' => array('organisation-name'),
'x-autocompletetype' => 'organization',
'autocomplete' => 'organization',
),
);
}

View File

@@ -6,8 +6,9 @@
function addressfield_field_views_data($field) {
$data = field_views_field_default_views_data($field);
// Add a handler for countries.
foreach ($field['storage']['details']['sql'] as $type => $tables) {
// Add a filter handler for countries.
$key = key($field['storage']['details']);
foreach ($field['storage']['details'][$key] as $type => $tables) {
foreach ($tables as $table_name => $columns) {
if (!isset($columns['country'])) {
continue;
@@ -22,5 +23,73 @@ function addressfield_field_views_data($field) {
}
}
// Only expose these components as Views field handlers.
$implemented = array(
'country' => 'addressfield_views_handler_field_country',
'administrative_area' => 'views_handler_field',
'sub_administrative_area' => 'views_handler_field',
'dependent_locality' => 'views_handler_field',
'locality' => 'views_handler_field',
'postal_code' => 'views_handler_field',
'thoroughfare' => 'views_handler_field',
'premise' => 'views_handler_field',
'sub_premise' => 'views_handler_field',
'organisation_name' => 'views_handler_field',
'name_line' => 'views_handler_field',
'first_name' => 'views_handler_field',
'last_name' => 'views_handler_field',
'data' => 'views_handler_field_serialized',
);
// Get the translated field information.
$properties = addressfield_data_property_info();
// Iterate over addressfield defined tables.
foreach ($data as &$table) {
// Make sure the parent Views field (addressfield) is defined.
if (isset($table[$field['field_name']]['field'])) {
// Use the parent field definition as a template for component columns.
$field_def = $table[$field['field_name']]['field'];
// Remove 'additional fields' from the field definition. We don't
// necessarily want all our sibling columns.
unset($field_def['additional fields']);
// Define the valid columns.
$valid_columns = array();
foreach ($implemented as $implement => $handler) {
$column_name = $field['field_name'] . '_' . $implement;
$valid_columns[$column_name] = $handler;
}
// Iterate over the addressfield components.
foreach ($table as $column_name => &$column) {
if (empty($column['field']) && isset($valid_columns[$column_name])) {
// Assign the default component definition.
$column['field'] = $field_def;
$column['field']['real field'] = $column_name;
$column['field']['handler'] = $valid_columns[$column_name];
// Assign human-friendly field labels for addressfield components.
$field_labels = field_views_field_label($field['field_name']);
$field_label = array_shift($field_labels);
$property = str_replace($field_def['field_name'] . '_', '', $column_name);
if (!empty($properties[$property])) {
$property_label = $properties[$property]['label'];
$title = t('@field-label - @property-label', array(
'@field-label' => $field_label,
'@property-label' => $property_label,
));
$column['title'] = $title;
$column['title short'] = $title;
}
}
}
}
}
return $data;
}

View File

@@ -0,0 +1,40 @@
<?php
/**
* Defines a field handler that can display the country name instead of the two
* character country code for an address field country value.
*/
class addressfield_views_handler_field_country extends views_handler_field {
function option_definition() {
$options = parent::option_definition();
$options['display_name'] = array('default' => TRUE);
return $options;
}
function options_form(&$form, &$form_state) {
parent::options_form($form, $form_state);
$form['display_name'] = array(
'#type' => 'checkbox',
'#title' => t('Display the localized country name instead of the two character country code'),
'#default_value' => $this->options['display_name'],
);
}
function get_value($values, $field = NULL) {
$value = parent::get_value($values, $field);
// If we have a value for the field, look for the country name in the
// Address Field options list array if specified.
if (!empty($value) && !empty($this->options['display_name'])) {
$countries = _addressfield_country_options_list();
if (!empty($countries[$value])) {
$value = $countries[$value];
}
}
return $value;
}
}