\n";
$output .= form_hidden("nid", $nid);
- $result = db_query("SELECT c.cid, c.pid, c.nid, c.subject, c.comment, c.timestamp, u.uid, u.name, u.data, c.score, c.users FROM {comments} c INNER JOIN {users} u ON c.uid = u.uid WHERE c.cid = %d AND c.status = 0 GROUP BY c.cid, c.pid, c.nid, c.subject, c.comment, c.timestamp, u.uid, u.name, u.data, c.score, c.users", $cid);
+ $result = db_query("SELECT c.cid, c.pid, c.nid, c.subject, c.comment, c.timestamp, u.uid, u.name, u.picture, u.data, c.score, c.users FROM {comments} c INNER JOIN {users} u ON c.uid = u.uid WHERE c.cid = %d AND c.status = 0 GROUP BY c.cid, c.pid, c.nid, c.subject, c.comment, c.timestamp, u.uid, u.name, u.picture, u.data, c.score, c.users", $cid);
if ($comment = db_fetch_object($result)) {
$output .= theme("comment_view", $comment, theme('links', module_invoke_all('link', 'comment', $comment, 1)));
@@ -576,9 +575,9 @@ function comment_render($node, $cid = 0) {
** Multiple comments view
*/
- $query .= "SELECT c.cid as cid, c.pid, c.nid, c.subject, c.comment, c.timestamp, u.uid, u.name, u.data, c.score, c.users, c.thread FROM {comments} c INNER JOIN {users} u ON c.uid = u.uid WHERE c.nid = '". check_query($nid) ."' AND c.status = 0";
+ $query .= "SELECT c.cid as cid, c.pid, c.nid, c.subject, c.comment, c.timestamp, u.uid, u.name, u.picture, u.data, c.score, c.users, c.thread FROM {comments} c INNER JOIN {users} u ON c.uid = u.uid WHERE c.nid = '". check_query($nid) ."' AND c.status = 0";
- $query .= " GROUP BY c.cid, c.pid, c.nid, c.subject, c.comment, c.timestamp, u.uid, u.name, u.data, c.score, c.users, c.thread";
+ $query .= " GROUP BY c.cid, c.pid, c.nid, c.subject, c.comment, c.timestamp, u.uid, u.name, u.picture, u.data, c.score, c.users, c.thread";
/*
** We want to use the standard pager, but threads would need every
diff --git a/modules/drupal.module b/modules/drupal.module
index 77a5c8f3a6f..b6392a501d4 100644
--- a/modules/drupal.module
+++ b/modules/drupal.module
@@ -185,22 +185,4 @@ function drupal_login($arguments) {
}
}
-function drupal_user($type, $edit, $user) {
-
- $module = "drupal";
- $name = module_invoke($module, "info", "name");
- switch ($type) {
- case "view_private":
- $result = user_get_authname($user, $module);
- $title = t("%name ID", array("%name" => $name));
- if ($result) {
- return form_item($title, $result);
- }
- else {
- // TODO: use a variation of $base_url instead of $HTTP_HOST below
- return form_item($title, "$user->name@". $_SERVER["HTTP_HOST"]);
- }
- }
-}
-
?>
diff --git a/modules/drupal/drupal.module b/modules/drupal/drupal.module
index 77a5c8f3a6f..b6392a501d4 100644
--- a/modules/drupal/drupal.module
+++ b/modules/drupal/drupal.module
@@ -185,22 +185,4 @@ function drupal_login($arguments) {
}
}
-function drupal_user($type, $edit, $user) {
-
- $module = "drupal";
- $name = module_invoke($module, "info", "name");
- switch ($type) {
- case "view_private":
- $result = user_get_authname($user, $module);
- $title = t("%name ID", array("%name" => $name));
- if ($result) {
- return form_item($title, $result);
- }
- else {
- // TODO: use a variation of $base_url instead of $HTTP_HOST below
- return form_item($title, "$user->name@". $_SERVER["HTTP_HOST"]);
- }
- }
-}
-
?>
diff --git a/modules/locale.module b/modules/locale.module
index eedba7595f6..907c99834f3 100644
--- a/modules/locale.module
+++ b/modules/locale.module
@@ -74,7 +74,7 @@ function locale_link($type) {
function locale_user($type, &$edit, &$user) {
global $languages;
- if ($type == "edit_form" && count($languages) > 1) {
+ if ($type == 'edit' && count($languages) > 1) {
return array(t('Locale settings') => form_radios(t("Language"), 'language', $user->language, $languages, t("Selecting a different language will change the language of the site.")));
}
}
diff --git a/modules/locale/locale.module b/modules/locale/locale.module
index eedba7595f6..907c99834f3 100644
--- a/modules/locale/locale.module
+++ b/modules/locale/locale.module
@@ -74,7 +74,7 @@ function locale_link($type) {
function locale_user($type, &$edit, &$user) {
global $languages;
- if ($type == "edit_form" && count($languages) > 1) {
+ if ($type == 'edit' && count($languages) > 1) {
return array(t('Locale settings') => form_radios(t("Language"), 'language', $user->language, $languages, t("Selecting a different language will change the language of the site.")));
}
}
diff --git a/modules/node.module b/modules/node.module
index 3e1a62155ae..16c7015d6b9 100644
--- a/modules/node.module
+++ b/modules/node.module
@@ -340,7 +340,7 @@ function node_load($conditions, $revision = -1) {
** Retrieve the node:
*/
- $node = db_fetch_object(db_query('SELECT n.*, u.uid, u.name, u.data FROM {node} n INNER JOIN {users} u ON u.uid = n.uid WHERE '. implode(' AND ', $cond)));
+ $node = db_fetch_object(db_query('SELECT n.*, u.uid, u.name, u.picture, u.data FROM {node} n INNER JOIN {users} u ON u.uid = n.uid WHERE '. implode(' AND ', $cond)));
$node = drupal_unpack($node);
/*
diff --git a/modules/node/node.module b/modules/node/node.module
index 3e1a62155ae..16c7015d6b9 100644
--- a/modules/node/node.module
+++ b/modules/node/node.module
@@ -340,7 +340,7 @@ function node_load($conditions, $revision = -1) {
** Retrieve the node:
*/
- $node = db_fetch_object(db_query('SELECT n.*, u.uid, u.name, u.data FROM {node} n INNER JOIN {users} u ON u.uid = n.uid WHERE '. implode(' AND ', $cond)));
+ $node = db_fetch_object(db_query('SELECT n.*, u.uid, u.name, u.picture, u.data FROM {node} n INNER JOIN {users} u ON u.uid = n.uid WHERE '. implode(' AND ', $cond)));
$node = drupal_unpack($node);
/*
diff --git a/modules/profile.module b/modules/profile.module
index a16c47c204f..d1e5e5f0c9a 100644
--- a/modules/profile.module
+++ b/modules/profile.module
@@ -1,306 +1,300 @@
array("textfield", t("Name"), "", 64, 64, ""),
- "address" => array("textfield", t("Address"), "", 64, 64, ""),
- "city" => array("textfield", t("City"), "", 64, 64, ""),
- "state" => array("textfield", t("State, province or region"), "", 64, 64, ""),
- "zip" => array("textfield", t("Zip or postal code"), "", 7, 10, ""),
- "country" => array("textfield", t("Country"), "", 64, 64, ""),
- "birthday" => array("", t("Birthday"), ""),
- "gender" => array("select", t("Gender"), "", array(0 => "-", "m" => t("male"), "f" => t("female")), "", 0, 0),
- "job" => array("textfield", t("Job title"), "", 64, 64, ""),
- "icq" => array("textfield", t("ICQ messenger ID"), "", 12, 12, ""),
- "msn" => array("textfield", t("MSN messenger ID"), "", 64, 64, ""),
- "yahoo" => array("textfield", t("Yahoo messenger ID"), "", 64, 64, ""),
- "aim" => array("textfield", t("AIM messenger ID"), "", 64, 64, ""),
- "homepage" => array("textfield", t("URL of homepage"), "", 64, 64, t("Make sure you enter a fully qualified URL: remember to include \"http://\".")),
- "biography" => array("textarea", t("Biography"), "", 64, 4, ""),
- "interests" => array("textarea", t("Interests"), "", 64, 4, ""),
- "publickey" => array("textarea", t("Public key"), "", 64, 4, ""),
- "avatar" => array("", t("Avatar or picture"), t("Your virtual face or picture. Maximum dimensions are %dimensions and the maximum size is %size kB.", array("%dimensions" => variable_get("profile_avatar_dimensions", "85x85"), "%size" => variable_get("profile_avatar_file_size", "30"))))
- );
-
- $GLOBALS["profile_days"] = array_merge(array(0 => t("day")), drupal_map_assoc(range(1, 31)));
- $GLOBALS["profile_months"] = array(0 => t("month"), 1 => t("January"), 2 => t("February"), 3 => t("March"), 4 => t("April"), 5 => t("May"), 6 => t("June"), 7 => t("July"), 8 => t("August"), 9 => t("September"), 10 => t("October"), 11 => t("November"), 12 => t("December"));
-}
+// TODO: add a 'date' field so we can migrate the birthday information.
function profile_help($section) {
- $output = "";
-
switch ($section) {
case 'admin/system/modules#description':
$output = t("Support for configurable user profiles.");
break;
- case 'admin/system/modules/profile':
- $output = t("When a user creates an account you can ask for some extra information, as well as letting the user have a small picture, called an avatar.
- In order for a user to enter information, you must check enable.
- In order for other people to see the entered information, you must make it public.
- If an item is public, but not enabled, the user can never give it a value and it will never be seen. Public does not imply enable.
", array("%edit" => url("user/edit")));
- break;
}
return $output;
+
+
+}
+
+function profile_link($type) {
+ if ($type == 'system') {
+ menu('profile', t('browse'), 'profile_browse', 0, MENU_HIDE);
+
+ if (user_access('administer users')) {
+ menu('admin/system/modules/profile', t('profile'), 'profile_admin_overview');
+ menu('admin/system/modules/profile/add', NULL, 'profile_admin_add', 0, MENU_HIDE);
+ menu('admin/system/modules/profile/edit', NULL, 'profile_admin_edit', 0, MENU_HIDE);
+ menu('admin/system/modules/profile/delete', NULL, 'profile_admin_delete', 0, MENU_HIDE);
+ }
+ }
+}
+
+function profile_browse() {
+
+ $value = arg(2) ? arg(2) : 1;
+
+ // Determine the field to group users by:
+ $field = db_fetch_object(db_query("SELECT DISTINCT(f.fid), f.type, f.title FROM {profile_fields} f INNER JOIN {profile_values} v ON f.fid = v.fid WHERE f.name = '%s' AND v.value = '%s' ORDER BY f.category, f.weight", arg(1), $value));
+
+ if ($field->fid) {
+ // Compile a list of fields to show:
+ $fields = array();
+ $result = db_query("SELECT name, title, type FROM {profile_fields} WHERE fid != %d AND overview = 1", $field->fid);
+ while ($record = db_fetch_object($result)) {
+ $fields[] = $record;
+ }
+
+ // Extract the affected users:
+ $result = pager_query("SELECT u.uid FROM {users} u INNER JOIN {profile_values} v ON u.uid = v.uid WHERE v.fid = $field->fid AND v.value = '". check_query($value) ."' ORDER BY u.changed DESC", 20);
+
+ $output = '';
+ while ($account = db_fetch_object($result)) {
+ $output .= theme('profile_profile', user_load(array('uid' => $account->uid)), $fields);
+ }
+ $output .= theme('pager', NULL, 20);
+
+ if ($field->type == "selection") {
+ $title = arg(2);
+ }
+ else {
+ $title = $field->title;
+ }
+
+ print theme('page', $output, $title);
+ }
+ else {
+ drupal_not_found();
+ }
+}
+
+function profile_load_profile(&$user) {
+ $result = db_query('SELECT f.name, v.value FROM {profile_fields} f INNER JOIN {profile_values} v ON f.fid = v.fid WHERE uid = %d', $user->uid);
+ while ($field = db_fetch_object($result)) {
+ if (empty($user->{$field->name})) {
+ $user->{$field->name} = $field->value;
+ }
+ }
+}
+
+function profile_save_profile($edit, $user) {
+ db_query('DELETE FROM {profile_values} WHERE uid = %d', $user->uid);
+ $result = db_query('SELECT fid, name FROM profile_fields');
+ while ($field = db_fetch_object($result)) {
+ if ($edit[$field->name]) {
+ db_query("INSERT INTO {profile_values} (fid, uid, value) VALUES (%d, %d, '%s')", $field->fid, $user->uid, $edit[$field->name]);
+ unset($edit[$field->name]);
+ }
+ }
+}
+
+function profile_view_profile($user) {
+
+ profile_load_profile(&$user);
+
+ $result = db_query('SELECT * FROM {profile_fields} ORDER BY category, weight');
+ while ($field = db_fetch_object($result)) {
+ if ($value = $user->{$field->name}) {
+ switch ($field->type) {
+ case 'textfield':
+ case 'textarea':
+ $output .= form_item($field->title, check_output($value));
+ break;
+ case 'selection':
+ $output .= form_item($field->title, l($value, "profile/$field->name/$value"));
+ break;
+ case 'checkbox':
+ $output .= '
'. l($field->title, "profile/$field->name/") .'
';
+ }
+ }
+ }
+
+ return $output;
}
-function profile_settings() {
- global $profile_fields;
+function profile_edit_profile($edit, $user) {
- if (!$profile_fields) {
- _profile_init();
+ $result = db_query('SELECT * FROM {profile_fields} ORDER BY category, weight');
+
+ while ($field = db_fetch_object($result)) {
+ switch ($field->type) {
+ case 'textfield':
+ $fields[$field->category] .= form_textfield($field->title, $field->name, $edit[$field->name], 70, 255, $field->explanation);
+ break;
+ case 'textarea':
+ $fields[$field->category] .= form_textarea($field->title, $field->name, $edit[$field->name], 60, 4, $field->explanation);
+ break;
+ case 'checkbox':
+ $fields[$field->category] .= form_checkbox($field->title, $field->name, 1, $edit[$field->name], $field->explanation);
+ break;
+ case 'selection':
+ $options = array('--');
+ $lines = split("[\n\r]", $field->options);
+ foreach ($lines as $line) {
+ if ($line = trim($line)) {
+ $options[$line] = $line;
+ }
+ }
+
+ $fields[$field->category] .= form_select($field->title, $field->name, $edit[$field->name], $options, $field->explanation);
+ break;
+ }
}
- if (!file_check_directory(file_create_path(variable_get('profile_avatar_path', 'avatars')))) {
- $error['profile_avatar_path'] = theme('error', t('Directory does not exist, or is not writable.'));
- }
-
- $profile_public_fields = variable_get("profile_public_fields", array());
- $profile_private_fields = variable_get("profile_private_fields", array());
- $profile_required_fields = variable_get("profile_required_fields", array());
-
- $header = array(t("field"), t("enable"), t("public"), t("required"));
- $i = 0;
- foreach ($profile_fields as $key => $field) {
- $row[$i][] = $field[1];
- $row[$i][] = form_checkbox("", "profile_private_fields][", $key, in_array($key, $profile_private_fields));
- $row[$i][] = form_checkbox("", "profile_public_fields][", $key, in_array($key, $profile_public_fields));
- $row[$i][] = form_checkbox("", "profile_required_fields][", $key, in_array($key, $profile_required_fields));
- $i++;
- }
-
- $avatar = form_textfield(t("Avatar image path"), "profile_avatar_path", variable_get("profile_avatar_path", "avatars"), 30, 255, t("Subdirectory in the directory '%dir' where avatars will be stored.", array('%dir' => variable_get('file_directory_path', 'files') . FILE_SEPARATOR)) . $error['profile_avatar_path']);
- $avatar .= form_textfield(t("Avatar maximum dimensions"), "profile_avatar_dimensions", variable_get("profile_avatar_dimensions", "85x85"), 10, 10, t("Maximum dimensions for avatars."));
- $avatar .= form_textfield(t("Avatar maximum file size"), "profile_avatar_file_size", variable_get("profile_avatar_file_size", "30"), 10, 10, t("Maximum file size for avatars, in kB."));
-
- $output = theme("table", $header, $row);
- $output .= form_group(t('Avatars'), $avatar);
-
- return $output;
+ return $fields;
}
function profile_user($type, $edit, &$user) {
- global $profile_fields;
- if (!$profile_fields) {
- _profile_init();
- }
-
switch ($type) {
- case "edit_form":
- // when user tries to edit his own data
- return _profile_form(object2array($user), "private");
- case "edit_validate":
- // validate user data editing
- return _profile_validate($edit, "private", $user);
- case "view_public":
- // when others look at user data
- return _profile_user_view($user, "public");
- case "view_private":
- // when user looks at his own data
- return _profile_user_view($user, "private");
+ case 'load':
+ return profile_load_profile($user);
+ case 'update':
+ return profile_save_profile($edit, $user);
+ case 'view':
+ return profile_view_profile($user);
+ case 'edit':
+ return profile_edit_profile($edit, $user);
+ case 'validate':
+ return $edit;
}
}
-function profile_required($title) {
- // this pleads "theme, theme" ;)
- return $title ." ". theme("mark");
+function profile_validate_form($edit) {
+
+ // Validate the title:
+
+ if (!$edit['title']) {
+ return t('You must enter a title.');
+ }
+
+ // Validate the 'form name':
+
+ if (eregi('[^a-z0-9_-]', $edit['name'])) {
+ return t('The specified form name contains one or more illegal characters. Spaces or any other special characters expect dash (-) and underscore (_) are not allowed.');
+ }
+
+ if (in_array($edit['name'], user_fields())) {
+ return t('The specified form name is reserved for use by Drupal.');
+ }
+
+ // Validate the category:
+
+ if (!$edit['category']) {
+ return t('You must enter a category.');
+ }
}
-function _profile_form($edit, $mode) {
- global $profile_fields, $user;
+function profile_admin_add($type) {
+ $type = _profile_field_types($type);
- $reg_fields = _profile_active_fields($mode);
- $required_fields = _profile_active_fields("required");
- foreach ($profile_fields as $name => $field) {
- if ($field[0] && in_array($name, $reg_fields)) {
- $f = "form_". $field[0];
- $t = "profile_". $name;
- $output .= $f((in_array($name, $required_fields) ? profile_required($field[1]) : $field[1]), $t, $edit[$t], $field[3], $field[4], $field[5], $field[6]);
+ if ($_POST['op']) {
+ $data = $_POST['edit'];
+
+ if ($error = profile_validate_form($data)) {
+ drupal_set_message($error, 'error');
+ }
+ else {
+ db_query("INSERT INTO {profile_fields} (title, name, explanation, category, type, weight, overview, options) VALUES ('%s', '%s', '%s', '%s', '%s', %d, %d, '%s')", $data['title'], $data['name'], $data['explanation'], $data['category'], $type, $data['weight'], $data['overview'], $data['options']);
+
+ drupal_set_message(t('the field has been created.'));
}
}
-
- if (in_array("birthday", $reg_fields)) {
- $output .= form_item((in_array("birthday", $required_fields) ? profile_required($profile_fields["birthday"][1]) : $profile_fields["birthday"][1]), _profile_edit_birth(array2object($edit)), $profile_fields["birthday"][2]);
+ else {
+ $data = array('name' => 'profile_');
}
- if (in_array("avatar", $reg_fields)) {
- if ($edit["profile_avatar"] && file_exists($edit["profile_avatar"])) {
- $output .= form_item(t("Avatar"), '
');
- }
- $output .= form_file($profile_fields["avatar"][1], "profile_avatar", 64, $profile_fields["avatar"][2]);
- }
-
- return array(t('Personal information') => $output);
+ print theme('page', _profile_field_form($type, $data), t('Add new %type', array('%type' => $type)));
}
-function _profile_validate($edit, $mode, $user) {
+function profile_admin_edit($fid) {
- global $profile_fields;
+ if ($_POST['op']) {
+ $data = $_POST['edit'];
- $enabled_fields = _profile_active_fields($mode);
+ if ($error = profile_validate_form($data)) {
+ drupal_set_message($error, 'error');
- if (in_array("birthday", $enabled_fields) && ($birth_error = _profile_validate_birth($edit))) {
- $error .= $birth_error ."
";
- }
+ }
+ else {
+ db_query("UPDATE {profile_fields} SET title = '%s', name = '%s', explanation = '%s', category = '%s', weight = %d, overview = %d, options = '%s' WHERE fid = %d", $data['title'], $data['name'], $data['explanation'], $data['category'], $data['weight'], $data['overview'], $data['options'], $fid);
- if (in_array("avatar", $enabled_fields) && ($avatar_error = _profile_validate_avatar($edit, $user))) {
- $error .= $avatar_error ."
";
- }
-
- foreach (array_keys($profile_fields) as $field) {
- // replicate any key which was saved during registration but is not in this form
- if (!$edit[$field] && $user->$field) {
- $edit[$field] = $user->$field;
+ drupal_set_message(t('the field has been updated.'));
}
}
+ else {
+ $data = db_fetch_array(db_query('SELECT * FROM {profile_fields} WHERE fid = %d', $fid));
+ }
- // now check for required fields
- foreach (_profile_active_fields("required") as $required) {
- if ($required != "0" && in_array($required, $enabled_fields)) {
- if (!$edit["profile_". $required]) {
- $error .= t("This required field is missing: %a", array("%a" => $profile_fields[$required][1])) ."
";
+ print theme('page', _profile_field_form($data['type'], $data), t('Edit %type', array('%type' => $edit['type'])));
+}
+
+function profile_admin_delete($fid) {
+ db_query('DELETE FROM {profile_fields} WHERE fid = %d', $fid);
+ drupal_set_message(t('the field has been deleted.'));
+ print theme('page', '', t('Delete field'));
+}
+
+function _profile_field_form($type, $edit = array()) {
+
+ $output = form_textfield(t('Title'), 'title', $edit['title'], 70, 128, t("The title of the new field. The title will be shown to the user. An example title is 'Favorite color'."), NULL, FORM_REQUIRED);
+ $output .= form_textfield(t('Form name'), 'name', $edit['name'], 70, 128, t("The name of the field. The form name is not shown to the user but used internally in the HTML code and URLs.
+Unless you know what you are doing, it is highly recommended that you prefix the form name with
profile_
to avoid name clashes with other fields. Because the form name's usage, spaces or any other special characters except dash (-) and underscore (_) are not allowed. An example for, name is 'profile_favorite_color' or just 'profile_color'."));
+ $output .= form_textarea(t('Explanation'), 'explanation', $edit['explanation'], 70, 3, t("An optional explanation to go with the new field. The explanation will be shown to the user."));
+ $output .= form_textfield(t('Category'), 'category', $edit['category'], 70, 128, t("The category the new field should be part of. Categories are used to group fields logically. An example category is 'Personal information'."));
+ $output .= form_weight(t('Weight'), 'weight', $edit['weight'], 5, t("The weights define the order in which the form fields are shown. Lighter fields \"float up\" towards the top of the category."));
+ $output .= form_checkbox(t('Display this field on member listsings'), 'overview', 1, $edit['overview']);
+
+ if ($type == 'selection') {
+ $output .= form_textarea(t('Selection options'), 'options', $edit['options'], 70, 8, t("A list op all options. Put each option on a separate line. Example options are 'red', 'blue', 'green', etc."));
+ }
+
+ $output .= form_submit(t('Save field'));
+
+ return form($output);
+}
+
+function profile_admin_overview() {
+
+ $result = db_query('SELECT * FROM {profile_fields} ORDER BY category, weight');
+ while ($field = db_fetch_object($result)) {
+ $rows[] = array($field->title, $field->name, $field->type, $field->category, l(t('edit'), "admin/system/modules/profile/edit/$field->fid"), l(t('delete'), "admin/system/modules/profile/delete/$field->fid"));
+ }
+
+ $header = array(t('title'), t('name'), t('type'), t('category'), array('data' => t('operations'), 'colspan' => '2'));
+
+ $output = theme('table', $header, $rows);
+ $output .= '
'. t('Create new field') .'
';
+ $output .= '
';
+ foreach (_profile_field_types() as $key => $value) {
+ $output .= "- ". l(t('Add new %type', array('%type' => $value)), "admin/system/modules/profile/add/$key") ."
";
+ }
+ $output .= '
';
+
+ print theme('page', $output);
+}
+
+function theme_profile_profile($user, $fields = array()) {
+
+ $output = "
\n";
+ $output .= theme('user_picture', $user);
+ $output .= "
". format_name($user) ."
\n";
+
+ foreach ($fields as $field) {
+ if ($user->{$field->name}) {
+ if ($field->type == 'checkbox') {
+ $output .= "
". $field->title ."
";
+ }
+ else {
+ $output .= "
". $user->{$field->name} ."
";
}
}
}
- return $error ? $error : $edit;
-}
+ $output .= "
\n";
-function _profile_user_view(&$user, $mode) {
- global $profile_fields;
-
- foreach (_profile_active_fields($mode) as $name) {
- $field = $profile_fields[$name];
- $t = "profile_". $name;
-
- if (!empty($user->$t)) {
- switch ($field[0]) {
- case "textfield":
- case "textarea":
- case "checkbox":
- $value = ($t == "profile_homepage") ? "
$t) ."\">". check_output($user->$t) ."" : check_output($user->$t);
- $output .= form_item($field[1], $value);
- break;
- case "select":
- $output .= form_item($field[1], check_output($profile_fields[$name][3][$user->$t]));
- break;
- case "":
- // special
- if ($t == "profile_avatar") {
- if (file_exists($user->$t)) {
- $output .= form_item(t("Avatar"), '
');
- }
- }
-
- if ($t == "profile_birthday") {
- if (isset($user->profile_birthday) && isset($user->profile_birthmonth) && isset($user->profile_birthyear)) {
- // this is very european-centric, can we use format_date?
- $time = mktime(0, 0, 0, $user->profile_birthmonth, $user->profile_birthday, $user->profile_birthyear);
- $output .= form_item(t("Birthday"), format_date($time, "custom", "F j, Y"));
- }
- }
- }
- }
- }
return $output;
}
-function profile_file_download($file) {
- if (strpos($file, variable_get("profile_avatar_path", "avatars") . FILE_SEPARATOR . 'avatar-') === 0) {
- list($width, $height, $type, $attr) = getimagesize(file_create_path($file));
- $types = array(
- IMAGETYPE_GIF => 'image/gif',
- IMAGETYPE_JPEG => 'image/jpeg',
- IMAGETYPE_PNG => 'image/png',
- IMAGETYPE_SWF => 'application/x-shockwave-flash',
- IMAGETYPE_PSD => 'image/psd',
- IMAGETYPE_BMP => 'image/bmp',
- IMAGETYPE_TIFF_II => 'image/tiff',
- IMAGETYPE_TIFF_MM => 'image/tiff',
- IMAGETYPE_JPC => 'application/octet-stream',
- IMAGETYPE_JP2 => 'image/jp2',
- IMAGETYPE_JPX => 'application/octet-stream',
- IMAGETYPE_JB2 => 'application/octet-stream',
- IMAGETYPE_SWC => 'application/x-shockwave-flash',
- IMAGETYPE_IFF => 'image/iff',
- IMAGETYPE_WBMP => 'image/vnd.wap.wbmp',
- IMAGETYPE_XBM => 'image/xbm'
- );
- return array('Content-type: '. $types[$type]);
- }
-}
-
-function _profile_validate_avatar(&$edit, $user) {
- // check that uploaded file is an image, with a maximum file size and maximum height/width
-
- unset($edit["profile_avatar"]);
-
- if (!$file = file_check_upload('profile_avatar')) {
- $edit["profile_avatar"] = $user->profile_avatar;
- return;
- }
-
- $extension = strtolower(strrchr($file->name, "."));
- $size = getimagesize($file->path);
- list($maxwidth, $maxheight) = explode("x", variable_get("profile_avatar_dimensions", "85x85"));
- if ((!in_array($size[2], array(1, 2, 3))) || (!in_array($extension, array(".gif", ".jpg", ".png", ".jpeg")))) {
- $error = t("The uploaded file was not an image.");
- }
- else if ($file->size > (variable_get("profile_avatar_file_size", "30") * 1000)) {
- $error = t("The uploaded image is too large; the maximum file size is %a kB.", array("%a" => variable_get("profile_avatar_file_size", "30")));
- }
- else if ($size[0] > $maxwidth || $size[1] > $maxheight) {
- $error = t("The uploaded image is too large; the maximum dimensions are %a pixels.", array("%a" => variable_get("profile_avatar_dimensions", "85x85")));
- }
- else if ($file = file_save_upload('profile_avatar', variable_get("profile_avatar_path", "avatars") . FILE_SEPARATOR .'avatar-'. $user->uid . $extension, 1)) {
- $edit["profile_avatar"] = $file->path;
- }
- else {
- $error = t("Failed to upload the avatar image; the '%directory' directory doesn't exist.", array("%directory" => variable_get("profile_avatar_path", "avatars")));
- }
-
- return $error ? "$error
" : "";
-}
-
-function _profile_active_fields($mode) {
- return variable_get("profile_". $mode ."_fields", array());
-}
-
-function _profile_edit_birth($edit = "") {
- global $profile_months, $profile_days;
- $output = _profile_select("profile_birthday", $edit->profile_birthday, $profile_days);
- $output .= " ";
- $output .= _profile_select("profile_birthmonth", $edit->profile_birthmonth, $profile_months);
- $output .= " ";
- $output .= "
profile_birthyear\" />";
- return $output;
-}
-
-function _profile_validate_birth(&$edit) {
- if (!$edit["profile_birthday"] && !$edit["profile_birthmonth"] && !$edit["profile_birthyear"]) {
- // change this if you want required birth
- return;
- }
-
- if ($edit["profile_birthyear"] > 1900 && checkdate($edit["profile_birthmonth"], $edit["profile_birthday"], $edit["profile_birthyear"])) {
- return;
- }
- else {
- return t("The specified birthday is not valid.") ."
";
- }
-}
-
-function _profile_select($name, $value, $options, $extra = 0, $multiple = 0) {
- if (count($options) > 0) {
- foreach ($options as $key=>$choice) {
- $select .= "
";
- }
- return "
";
- }
+function _profile_field_types($type = NULL) {
+ $types = array('textfield', 'textarea', 'checkbox', 'selection');
+ return isset($type) ? $types[$type] : $types;
}
?>
diff --git a/modules/profile/profile.module b/modules/profile/profile.module
index a16c47c204f..d1e5e5f0c9a 100644
--- a/modules/profile/profile.module
+++ b/modules/profile/profile.module
@@ -1,306 +1,300 @@
array("textfield", t("Name"), "", 64, 64, ""),
- "address" => array("textfield", t("Address"), "", 64, 64, ""),
- "city" => array("textfield", t("City"), "", 64, 64, ""),
- "state" => array("textfield", t("State, province or region"), "", 64, 64, ""),
- "zip" => array("textfield", t("Zip or postal code"), "", 7, 10, ""),
- "country" => array("textfield", t("Country"), "", 64, 64, ""),
- "birthday" => array("", t("Birthday"), ""),
- "gender" => array("select", t("Gender"), "", array(0 => "-", "m" => t("male"), "f" => t("female")), "", 0, 0),
- "job" => array("textfield", t("Job title"), "", 64, 64, ""),
- "icq" => array("textfield", t("ICQ messenger ID"), "", 12, 12, ""),
- "msn" => array("textfield", t("MSN messenger ID"), "", 64, 64, ""),
- "yahoo" => array("textfield", t("Yahoo messenger ID"), "", 64, 64, ""),
- "aim" => array("textfield", t("AIM messenger ID"), "", 64, 64, ""),
- "homepage" => array("textfield", t("URL of homepage"), "", 64, 64, t("Make sure you enter a fully qualified URL: remember to include \"http://\".")),
- "biography" => array("textarea", t("Biography"), "", 64, 4, ""),
- "interests" => array("textarea", t("Interests"), "", 64, 4, ""),
- "publickey" => array("textarea", t("Public key"), "", 64, 4, ""),
- "avatar" => array("", t("Avatar or picture"), t("Your virtual face or picture. Maximum dimensions are %dimensions and the maximum size is %size kB.", array("%dimensions" => variable_get("profile_avatar_dimensions", "85x85"), "%size" => variable_get("profile_avatar_file_size", "30"))))
- );
-
- $GLOBALS["profile_days"] = array_merge(array(0 => t("day")), drupal_map_assoc(range(1, 31)));
- $GLOBALS["profile_months"] = array(0 => t("month"), 1 => t("January"), 2 => t("February"), 3 => t("March"), 4 => t("April"), 5 => t("May"), 6 => t("June"), 7 => t("July"), 8 => t("August"), 9 => t("September"), 10 => t("October"), 11 => t("November"), 12 => t("December"));
-}
+// TODO: add a 'date' field so we can migrate the birthday information.
function profile_help($section) {
- $output = "";
-
switch ($section) {
case 'admin/system/modules#description':
$output = t("Support for configurable user profiles.");
break;
- case 'admin/system/modules/profile':
- $output = t("When a user creates an account you can ask for some extra information, as well as letting the user have a small picture, called an avatar.
- In order for a user to enter information, you must check enable.
- In order for other people to see the entered information, you must make it public.
- If an item is public, but not enabled, the user can never give it a value and it will never be seen. Public does not imply enable.
", array("%edit" => url("user/edit")));
- break;
}
return $output;
+
+
+}
+
+function profile_link($type) {
+ if ($type == 'system') {
+ menu('profile', t('browse'), 'profile_browse', 0, MENU_HIDE);
+
+ if (user_access('administer users')) {
+ menu('admin/system/modules/profile', t('profile'), 'profile_admin_overview');
+ menu('admin/system/modules/profile/add', NULL, 'profile_admin_add', 0, MENU_HIDE);
+ menu('admin/system/modules/profile/edit', NULL, 'profile_admin_edit', 0, MENU_HIDE);
+ menu('admin/system/modules/profile/delete', NULL, 'profile_admin_delete', 0, MENU_HIDE);
+ }
+ }
+}
+
+function profile_browse() {
+
+ $value = arg(2) ? arg(2) : 1;
+
+ // Determine the field to group users by:
+ $field = db_fetch_object(db_query("SELECT DISTINCT(f.fid), f.type, f.title FROM {profile_fields} f INNER JOIN {profile_values} v ON f.fid = v.fid WHERE f.name = '%s' AND v.value = '%s' ORDER BY f.category, f.weight", arg(1), $value));
+
+ if ($field->fid) {
+ // Compile a list of fields to show:
+ $fields = array();
+ $result = db_query("SELECT name, title, type FROM {profile_fields} WHERE fid != %d AND overview = 1", $field->fid);
+ while ($record = db_fetch_object($result)) {
+ $fields[] = $record;
+ }
+
+ // Extract the affected users:
+ $result = pager_query("SELECT u.uid FROM {users} u INNER JOIN {profile_values} v ON u.uid = v.uid WHERE v.fid = $field->fid AND v.value = '". check_query($value) ."' ORDER BY u.changed DESC", 20);
+
+ $output = '';
+ while ($account = db_fetch_object($result)) {
+ $output .= theme('profile_profile', user_load(array('uid' => $account->uid)), $fields);
+ }
+ $output .= theme('pager', NULL, 20);
+
+ if ($field->type == "selection") {
+ $title = arg(2);
+ }
+ else {
+ $title = $field->title;
+ }
+
+ print theme('page', $output, $title);
+ }
+ else {
+ drupal_not_found();
+ }
+}
+
+function profile_load_profile(&$user) {
+ $result = db_query('SELECT f.name, v.value FROM {profile_fields} f INNER JOIN {profile_values} v ON f.fid = v.fid WHERE uid = %d', $user->uid);
+ while ($field = db_fetch_object($result)) {
+ if (empty($user->{$field->name})) {
+ $user->{$field->name} = $field->value;
+ }
+ }
+}
+
+function profile_save_profile($edit, $user) {
+ db_query('DELETE FROM {profile_values} WHERE uid = %d', $user->uid);
+ $result = db_query('SELECT fid, name FROM profile_fields');
+ while ($field = db_fetch_object($result)) {
+ if ($edit[$field->name]) {
+ db_query("INSERT INTO {profile_values} (fid, uid, value) VALUES (%d, %d, '%s')", $field->fid, $user->uid, $edit[$field->name]);
+ unset($edit[$field->name]);
+ }
+ }
+}
+
+function profile_view_profile($user) {
+
+ profile_load_profile(&$user);
+
+ $result = db_query('SELECT * FROM {profile_fields} ORDER BY category, weight');
+ while ($field = db_fetch_object($result)) {
+ if ($value = $user->{$field->name}) {
+ switch ($field->type) {
+ case 'textfield':
+ case 'textarea':
+ $output .= form_item($field->title, check_output($value));
+ break;
+ case 'selection':
+ $output .= form_item($field->title, l($value, "profile/$field->name/$value"));
+ break;
+ case 'checkbox':
+ $output .= '
'. l($field->title, "profile/$field->name/") .'
';
+ }
+ }
+ }
+
+ return $output;
}
-function profile_settings() {
- global $profile_fields;
+function profile_edit_profile($edit, $user) {
- if (!$profile_fields) {
- _profile_init();
+ $result = db_query('SELECT * FROM {profile_fields} ORDER BY category, weight');
+
+ while ($field = db_fetch_object($result)) {
+ switch ($field->type) {
+ case 'textfield':
+ $fields[$field->category] .= form_textfield($field->title, $field->name, $edit[$field->name], 70, 255, $field->explanation);
+ break;
+ case 'textarea':
+ $fields[$field->category] .= form_textarea($field->title, $field->name, $edit[$field->name], 60, 4, $field->explanation);
+ break;
+ case 'checkbox':
+ $fields[$field->category] .= form_checkbox($field->title, $field->name, 1, $edit[$field->name], $field->explanation);
+ break;
+ case 'selection':
+ $options = array('--');
+ $lines = split("[\n\r]", $field->options);
+ foreach ($lines as $line) {
+ if ($line = trim($line)) {
+ $options[$line] = $line;
+ }
+ }
+
+ $fields[$field->category] .= form_select($field->title, $field->name, $edit[$field->name], $options, $field->explanation);
+ break;
+ }
}
- if (!file_check_directory(file_create_path(variable_get('profile_avatar_path', 'avatars')))) {
- $error['profile_avatar_path'] = theme('error', t('Directory does not exist, or is not writable.'));
- }
-
- $profile_public_fields = variable_get("profile_public_fields", array());
- $profile_private_fields = variable_get("profile_private_fields", array());
- $profile_required_fields = variable_get("profile_required_fields", array());
-
- $header = array(t("field"), t("enable"), t("public"), t("required"));
- $i = 0;
- foreach ($profile_fields as $key => $field) {
- $row[$i][] = $field[1];
- $row[$i][] = form_checkbox("", "profile_private_fields][", $key, in_array($key, $profile_private_fields));
- $row[$i][] = form_checkbox("", "profile_public_fields][", $key, in_array($key, $profile_public_fields));
- $row[$i][] = form_checkbox("", "profile_required_fields][", $key, in_array($key, $profile_required_fields));
- $i++;
- }
-
- $avatar = form_textfield(t("Avatar image path"), "profile_avatar_path", variable_get("profile_avatar_path", "avatars"), 30, 255, t("Subdirectory in the directory '%dir' where avatars will be stored.", array('%dir' => variable_get('file_directory_path', 'files') . FILE_SEPARATOR)) . $error['profile_avatar_path']);
- $avatar .= form_textfield(t("Avatar maximum dimensions"), "profile_avatar_dimensions", variable_get("profile_avatar_dimensions", "85x85"), 10, 10, t("Maximum dimensions for avatars."));
- $avatar .= form_textfield(t("Avatar maximum file size"), "profile_avatar_file_size", variable_get("profile_avatar_file_size", "30"), 10, 10, t("Maximum file size for avatars, in kB."));
-
- $output = theme("table", $header, $row);
- $output .= form_group(t('Avatars'), $avatar);
-
- return $output;
+ return $fields;
}
function profile_user($type, $edit, &$user) {
- global $profile_fields;
- if (!$profile_fields) {
- _profile_init();
- }
-
switch ($type) {
- case "edit_form":
- // when user tries to edit his own data
- return _profile_form(object2array($user), "private");
- case "edit_validate":
- // validate user data editing
- return _profile_validate($edit, "private", $user);
- case "view_public":
- // when others look at user data
- return _profile_user_view($user, "public");
- case "view_private":
- // when user looks at his own data
- return _profile_user_view($user, "private");
+ case 'load':
+ return profile_load_profile($user);
+ case 'update':
+ return profile_save_profile($edit, $user);
+ case 'view':
+ return profile_view_profile($user);
+ case 'edit':
+ return profile_edit_profile($edit, $user);
+ case 'validate':
+ return $edit;
}
}
-function profile_required($title) {
- // this pleads "theme, theme" ;)
- return $title ." ". theme("mark");
+function profile_validate_form($edit) {
+
+ // Validate the title:
+
+ if (!$edit['title']) {
+ return t('You must enter a title.');
+ }
+
+ // Validate the 'form name':
+
+ if (eregi('[^a-z0-9_-]', $edit['name'])) {
+ return t('The specified form name contains one or more illegal characters. Spaces or any other special characters expect dash (-) and underscore (_) are not allowed.');
+ }
+
+ if (in_array($edit['name'], user_fields())) {
+ return t('The specified form name is reserved for use by Drupal.');
+ }
+
+ // Validate the category:
+
+ if (!$edit['category']) {
+ return t('You must enter a category.');
+ }
}
-function _profile_form($edit, $mode) {
- global $profile_fields, $user;
+function profile_admin_add($type) {
+ $type = _profile_field_types($type);
- $reg_fields = _profile_active_fields($mode);
- $required_fields = _profile_active_fields("required");
- foreach ($profile_fields as $name => $field) {
- if ($field[0] && in_array($name, $reg_fields)) {
- $f = "form_". $field[0];
- $t = "profile_". $name;
- $output .= $f((in_array($name, $required_fields) ? profile_required($field[1]) : $field[1]), $t, $edit[$t], $field[3], $field[4], $field[5], $field[6]);
+ if ($_POST['op']) {
+ $data = $_POST['edit'];
+
+ if ($error = profile_validate_form($data)) {
+ drupal_set_message($error, 'error');
+ }
+ else {
+ db_query("INSERT INTO {profile_fields} (title, name, explanation, category, type, weight, overview, options) VALUES ('%s', '%s', '%s', '%s', '%s', %d, %d, '%s')", $data['title'], $data['name'], $data['explanation'], $data['category'], $type, $data['weight'], $data['overview'], $data['options']);
+
+ drupal_set_message(t('the field has been created.'));
}
}
-
- if (in_array("birthday", $reg_fields)) {
- $output .= form_item((in_array("birthday", $required_fields) ? profile_required($profile_fields["birthday"][1]) : $profile_fields["birthday"][1]), _profile_edit_birth(array2object($edit)), $profile_fields["birthday"][2]);
+ else {
+ $data = array('name' => 'profile_');
}
- if (in_array("avatar", $reg_fields)) {
- if ($edit["profile_avatar"] && file_exists($edit["profile_avatar"])) {
- $output .= form_item(t("Avatar"), '
');
- }
- $output .= form_file($profile_fields["avatar"][1], "profile_avatar", 64, $profile_fields["avatar"][2]);
- }
-
- return array(t('Personal information') => $output);
+ print theme('page', _profile_field_form($type, $data), t('Add new %type', array('%type' => $type)));
}
-function _profile_validate($edit, $mode, $user) {
+function profile_admin_edit($fid) {
- global $profile_fields;
+ if ($_POST['op']) {
+ $data = $_POST['edit'];
- $enabled_fields = _profile_active_fields($mode);
+ if ($error = profile_validate_form($data)) {
+ drupal_set_message($error, 'error');
- if (in_array("birthday", $enabled_fields) && ($birth_error = _profile_validate_birth($edit))) {
- $error .= $birth_error ."
";
- }
+ }
+ else {
+ db_query("UPDATE {profile_fields} SET title = '%s', name = '%s', explanation = '%s', category = '%s', weight = %d, overview = %d, options = '%s' WHERE fid = %d", $data['title'], $data['name'], $data['explanation'], $data['category'], $data['weight'], $data['overview'], $data['options'], $fid);
- if (in_array("avatar", $enabled_fields) && ($avatar_error = _profile_validate_avatar($edit, $user))) {
- $error .= $avatar_error ."
";
- }
-
- foreach (array_keys($profile_fields) as $field) {
- // replicate any key which was saved during registration but is not in this form
- if (!$edit[$field] && $user->$field) {
- $edit[$field] = $user->$field;
+ drupal_set_message(t('the field has been updated.'));
}
}
+ else {
+ $data = db_fetch_array(db_query('SELECT * FROM {profile_fields} WHERE fid = %d', $fid));
+ }
- // now check for required fields
- foreach (_profile_active_fields("required") as $required) {
- if ($required != "0" && in_array($required, $enabled_fields)) {
- if (!$edit["profile_". $required]) {
- $error .= t("This required field is missing: %a", array("%a" => $profile_fields[$required][1])) ."
";
+ print theme('page', _profile_field_form($data['type'], $data), t('Edit %type', array('%type' => $edit['type'])));
+}
+
+function profile_admin_delete($fid) {
+ db_query('DELETE FROM {profile_fields} WHERE fid = %d', $fid);
+ drupal_set_message(t('the field has been deleted.'));
+ print theme('page', '', t('Delete field'));
+}
+
+function _profile_field_form($type, $edit = array()) {
+
+ $output = form_textfield(t('Title'), 'title', $edit['title'], 70, 128, t("The title of the new field. The title will be shown to the user. An example title is 'Favorite color'."), NULL, FORM_REQUIRED);
+ $output .= form_textfield(t('Form name'), 'name', $edit['name'], 70, 128, t("The name of the field. The form name is not shown to the user but used internally in the HTML code and URLs.
+Unless you know what you are doing, it is highly recommended that you prefix the form name with
profile_
to avoid name clashes with other fields. Because the form name's usage, spaces or any other special characters except dash (-) and underscore (_) are not allowed. An example for, name is 'profile_favorite_color' or just 'profile_color'."));
+ $output .= form_textarea(t('Explanation'), 'explanation', $edit['explanation'], 70, 3, t("An optional explanation to go with the new field. The explanation will be shown to the user."));
+ $output .= form_textfield(t('Category'), 'category', $edit['category'], 70, 128, t("The category the new field should be part of. Categories are used to group fields logically. An example category is 'Personal information'."));
+ $output .= form_weight(t('Weight'), 'weight', $edit['weight'], 5, t("The weights define the order in which the form fields are shown. Lighter fields \"float up\" towards the top of the category."));
+ $output .= form_checkbox(t('Display this field on member listsings'), 'overview', 1, $edit['overview']);
+
+ if ($type == 'selection') {
+ $output .= form_textarea(t('Selection options'), 'options', $edit['options'], 70, 8, t("A list op all options. Put each option on a separate line. Example options are 'red', 'blue', 'green', etc."));
+ }
+
+ $output .= form_submit(t('Save field'));
+
+ return form($output);
+}
+
+function profile_admin_overview() {
+
+ $result = db_query('SELECT * FROM {profile_fields} ORDER BY category, weight');
+ while ($field = db_fetch_object($result)) {
+ $rows[] = array($field->title, $field->name, $field->type, $field->category, l(t('edit'), "admin/system/modules/profile/edit/$field->fid"), l(t('delete'), "admin/system/modules/profile/delete/$field->fid"));
+ }
+
+ $header = array(t('title'), t('name'), t('type'), t('category'), array('data' => t('operations'), 'colspan' => '2'));
+
+ $output = theme('table', $header, $rows);
+ $output .= '
'. t('Create new field') .'
';
+ $output .= '
';
+ foreach (_profile_field_types() as $key => $value) {
+ $output .= "- ". l(t('Add new %type', array('%type' => $value)), "admin/system/modules/profile/add/$key") ."
";
+ }
+ $output .= '
';
+
+ print theme('page', $output);
+}
+
+function theme_profile_profile($user, $fields = array()) {
+
+ $output = "
\n";
+ $output .= theme('user_picture', $user);
+ $output .= "
". format_name($user) ."
\n";
+
+ foreach ($fields as $field) {
+ if ($user->{$field->name}) {
+ if ($field->type == 'checkbox') {
+ $output .= "
". $field->title ."
";
+ }
+ else {
+ $output .= "
". $user->{$field->name} ."
";
}
}
}
- return $error ? $error : $edit;
-}
+ $output .= "
\n";
-function _profile_user_view(&$user, $mode) {
- global $profile_fields;
-
- foreach (_profile_active_fields($mode) as $name) {
- $field = $profile_fields[$name];
- $t = "profile_". $name;
-
- if (!empty($user->$t)) {
- switch ($field[0]) {
- case "textfield":
- case "textarea":
- case "checkbox":
- $value = ($t == "profile_homepage") ? "
$t) ."\">". check_output($user->$t) ."" : check_output($user->$t);
- $output .= form_item($field[1], $value);
- break;
- case "select":
- $output .= form_item($field[1], check_output($profile_fields[$name][3][$user->$t]));
- break;
- case "":
- // special
- if ($t == "profile_avatar") {
- if (file_exists($user->$t)) {
- $output .= form_item(t("Avatar"), '
');
- }
- }
-
- if ($t == "profile_birthday") {
- if (isset($user->profile_birthday) && isset($user->profile_birthmonth) && isset($user->profile_birthyear)) {
- // this is very european-centric, can we use format_date?
- $time = mktime(0, 0, 0, $user->profile_birthmonth, $user->profile_birthday, $user->profile_birthyear);
- $output .= form_item(t("Birthday"), format_date($time, "custom", "F j, Y"));
- }
- }
- }
- }
- }
return $output;
}
-function profile_file_download($file) {
- if (strpos($file, variable_get("profile_avatar_path", "avatars") . FILE_SEPARATOR . 'avatar-') === 0) {
- list($width, $height, $type, $attr) = getimagesize(file_create_path($file));
- $types = array(
- IMAGETYPE_GIF => 'image/gif',
- IMAGETYPE_JPEG => 'image/jpeg',
- IMAGETYPE_PNG => 'image/png',
- IMAGETYPE_SWF => 'application/x-shockwave-flash',
- IMAGETYPE_PSD => 'image/psd',
- IMAGETYPE_BMP => 'image/bmp',
- IMAGETYPE_TIFF_II => 'image/tiff',
- IMAGETYPE_TIFF_MM => 'image/tiff',
- IMAGETYPE_JPC => 'application/octet-stream',
- IMAGETYPE_JP2 => 'image/jp2',
- IMAGETYPE_JPX => 'application/octet-stream',
- IMAGETYPE_JB2 => 'application/octet-stream',
- IMAGETYPE_SWC => 'application/x-shockwave-flash',
- IMAGETYPE_IFF => 'image/iff',
- IMAGETYPE_WBMP => 'image/vnd.wap.wbmp',
- IMAGETYPE_XBM => 'image/xbm'
- );
- return array('Content-type: '. $types[$type]);
- }
-}
-
-function _profile_validate_avatar(&$edit, $user) {
- // check that uploaded file is an image, with a maximum file size and maximum height/width
-
- unset($edit["profile_avatar"]);
-
- if (!$file = file_check_upload('profile_avatar')) {
- $edit["profile_avatar"] = $user->profile_avatar;
- return;
- }
-
- $extension = strtolower(strrchr($file->name, "."));
- $size = getimagesize($file->path);
- list($maxwidth, $maxheight) = explode("x", variable_get("profile_avatar_dimensions", "85x85"));
- if ((!in_array($size[2], array(1, 2, 3))) || (!in_array($extension, array(".gif", ".jpg", ".png", ".jpeg")))) {
- $error = t("The uploaded file was not an image.");
- }
- else if ($file->size > (variable_get("profile_avatar_file_size", "30") * 1000)) {
- $error = t("The uploaded image is too large; the maximum file size is %a kB.", array("%a" => variable_get("profile_avatar_file_size", "30")));
- }
- else if ($size[0] > $maxwidth || $size[1] > $maxheight) {
- $error = t("The uploaded image is too large; the maximum dimensions are %a pixels.", array("%a" => variable_get("profile_avatar_dimensions", "85x85")));
- }
- else if ($file = file_save_upload('profile_avatar', variable_get("profile_avatar_path", "avatars") . FILE_SEPARATOR .'avatar-'. $user->uid . $extension, 1)) {
- $edit["profile_avatar"] = $file->path;
- }
- else {
- $error = t("Failed to upload the avatar image; the '%directory' directory doesn't exist.", array("%directory" => variable_get("profile_avatar_path", "avatars")));
- }
-
- return $error ? "$error
" : "";
-}
-
-function _profile_active_fields($mode) {
- return variable_get("profile_". $mode ."_fields", array());
-}
-
-function _profile_edit_birth($edit = "") {
- global $profile_months, $profile_days;
- $output = _profile_select("profile_birthday", $edit->profile_birthday, $profile_days);
- $output .= " ";
- $output .= _profile_select("profile_birthmonth", $edit->profile_birthmonth, $profile_months);
- $output .= " ";
- $output .= "
profile_birthyear\" />";
- return $output;
-}
-
-function _profile_validate_birth(&$edit) {
- if (!$edit["profile_birthday"] && !$edit["profile_birthmonth"] && !$edit["profile_birthyear"]) {
- // change this if you want required birth
- return;
- }
-
- if ($edit["profile_birthyear"] > 1900 && checkdate($edit["profile_birthmonth"], $edit["profile_birthday"], $edit["profile_birthyear"])) {
- return;
- }
- else {
- return t("The specified birthday is not valid.") ."
";
- }
-}
-
-function _profile_select($name, $value, $options, $extra = 0, $multiple = 0) {
- if (count($options) > 0) {
- foreach ($options as $key=>$choice) {
- $select .= "
";
- }
- return "
";
- }
+function _profile_field_types($type = NULL) {
+ $types = array('textfield', 'textarea', 'checkbox', 'selection');
+ return isset($type) ? $types[$type] : $types;
}
?>
diff --git a/modules/system.module b/modules/system.module
index 046920158cf..7169250d5d6 100644
--- a/modules/system.module
+++ b/modules/system.module
@@ -77,7 +77,7 @@ function system_link($type) {
}
function system_user($type, $edit, &$user) {
- if ($type == "edit_form") {
+ if ($type == 'edit') {
$options = "
\n";
if (count($themes = list_themes()) > 1) {
foreach ($themes as $key => $value) {
diff --git a/modules/system/system.module b/modules/system/system.module
index 046920158cf..7169250d5d6 100644
--- a/modules/system/system.module
+++ b/modules/system/system.module
@@ -77,7 +77,7 @@ function system_link($type) {
}
function system_user($type, $edit, &$user) {
- if ($type == "edit_form") {
+ if ($type == 'edit') {
$options = "
\n";
if (count($themes = list_themes()) > 1) {
foreach ($themes as $key => $value) {
diff --git a/modules/tracker.module b/modules/tracker.module
index 6bbc80f4347..8e5d8a11c6a 100644
--- a/modules/tracker.module
+++ b/modules/tracker.module
@@ -79,12 +79,8 @@ function tracker_posts($id = 0) {
}
function tracker_user($type, &$edit, &$user) {
- switch ($type) {
- case "view_private":
- case "view_public":
- if (user_access("access content")) {
- return form_item(t("Recent posts"), l(t("recent posts"), "tracker/$user->uid"));
- }
+ if ($type == 'view' && user_access("access content")) {
+ return form_item(t("Recent posts"), l(t("recent posts"), "tracker/$user->uid"));
}
}
diff --git a/modules/tracker/tracker.module b/modules/tracker/tracker.module
index 6bbc80f4347..8e5d8a11c6a 100644
--- a/modules/tracker/tracker.module
+++ b/modules/tracker/tracker.module
@@ -79,12 +79,8 @@ function tracker_posts($id = 0) {
}
function tracker_user($type, &$edit, &$user) {
- switch ($type) {
- case "view_private":
- case "view_public":
- if (user_access("access content")) {
- return form_item(t("Recent posts"), l(t("recent posts"), "tracker/$user->uid"));
- }
+ if ($type == 'view' && user_access("access content")) {
+ return form_item(t("Recent posts"), l(t("recent posts"), "tracker/$user->uid"));
}
}
diff --git a/modules/user.module b/modules/user.module
index 68d25921a2d..1dbc33dafe4 100644
--- a/modules/user.module
+++ b/modules/user.module
@@ -78,12 +78,13 @@ function user_save($account, $array = array()) {
$query .= "data = '%s', ";
$v[] = serialize($data);
- db_query("UPDATE {users} SET $query timestamp = %d WHERE uid = %d", array_merge($v, array(time(), $account->uid)));
+ db_query("UPDATE {users} SET $query changed = %d WHERE uid = %d", array_merge($v, array(time(), $account->uid)));
$user = user_load(array('uid' => $account->uid));
}
else {
- $array['timestamp'] = time();
+ $array['created'] = time();
+ $array['changed'] = time();
$array['uid'] = db_next_id("{users}_uid");
foreach ($array as $key => $value) {
@@ -112,11 +113,11 @@ function user_save($account, $array = array()) {
$user = user_load(array('name' => $array['name']));
- module_invoke_all('user', "insert", $array, $user);
+ module_invoke_all('user', 'insert', $array, $user);
}
foreach ($array as $key => $value) {
- if (substr($key, 0, 4) == "auth") {
+ if (substr($key, 0, 4) == 'auth') {
$authmaps[$key] = $value;
}
}
@@ -136,7 +137,7 @@ function user_validate_name($name) {
if (!$name) return t("You must enter a username.");
if (substr($name, 0, 1) == ' ') return t("The username cannot begin with a space.");
if (substr($name, -1) == ' ') return t("The username cannot end with a space.");
- if (ereg(" ", $name)) return t("The username cannot contain multiple spaces in a row.");
+ if (ereg(' ', $name)) return t("The username cannot contain multiple spaces in a row.");
if (ereg('[^ [:alnum:]@_.-]', $name)) return t("The username contains an illegal character.");
if (ereg('@', $name) && !eregi('@([0-9a-z](-?[0-9a-z])*.)+[a-z]{2}([zmuvtg]|fo|me)?$', $name)) return t("The username is not a valid authentication ID.");
if (strlen($name) > 56) return t("The username '%name' is too long: it must be less than 56 characters.", array("%name" => $name));
@@ -149,6 +150,35 @@ function user_validate_mail($mail) {
}
}
+function user_validate_picture($file, &$edit, $user) {
+
+ // initialize the picture:
+ $edit['picture'] = $user->picture;
+
+ // check that uploaded file is an image, with a maximum file size and maximum height/width
+ $extension = strtolower(strrchr($file->name, "."));
+ $size = getimagesize($file->path);
+ list($maxwidth, $maxheight) = explode("x", variable_get('user_picture_dimensions', "85x85"));
+
+ if ((!in_array($size[2], array(1, 2, 3))) || (!in_array($extension, array(".gif", ".jpg", ".png", ".jpeg")))) {
+ $error = t("The uploaded file was not an image.");
+ }
+ else if ($file->size > (variable_get('user_picture_file_size', "30") * 1000)) {
+ $error = t("The uploaded image is too large; the maximum file size is %a kB.", array("%a" => variable_get('user_picture_file_size', "30")));
+ }
+ else if ($size[0] > $maxwidth || $size[1] > $maxheight) {
+ $error = t("The uploaded image is too large; the maximum dimensions are %a pixels.", array("%a" => variable_get('user_picture_dimensions', "85x85")));
+ }
+ else if ($file = file_save_upload('picture', variable_get('user_picture_path', "pictures") . FILE_SEPARATOR .'picture-'. $user->uid . $extension, 1)) {
+ $edit['picture'] = $file->path;
+ }
+ else {
+ $error = t("Failed to upload the picture image; the '%directory' directory doesn't exist.", array("%directory" => variable_get('user_picture_path', "pictures")));
+ }
+
+ return $error;
+}
+
function user_validate_authmap($account, $authname, $module) {
$result = db_query("SELECT COUNT(*) from {authmap} WHERE uid != %d AND authname = '%s'", $account->uid, $authname);
if (db_result($result) > 0) {
@@ -281,7 +311,7 @@ function user_fields() {
}
else {
// Make sure we return the default fields at least
- $fields = array('uid', 'name', 'pass', "mail", "mode", "sort", "threshold", "theme", "signature", "timestamp", "status", "timezone", "language", "init", "data", "rid");
+ $fields = array('uid', 'name', 'pass', "mail", "picture", "mode", "sort", "threshold", "theme", "signature", "created", "changed", "status", "timezone", "language", "init", "data", "rid");
}
}
@@ -428,6 +458,42 @@ function user_block($op = "list", $delta = 0) {
}
}
+function theme_user_picture($account) {
+ if (variable_get('user_pictures', 0)) {
+ if ($account->picture && file_exists($account->picture)) {
+ $picture = file_create_url($account->picture);
+ }
+ else if (variable_get('user_picture_default', '')) {
+ $picture = variable_get('user_picture_default', '');
+ }
+
+ if ($picture) {
+ $picture = "
$account->name ? $account->name : t(variable_get("anonymous", "Anonymous")))) . "\" />";
+ if ($account->uid) {
+ $picture = l($picture, "user/view/$account->uid", array("title" => t("View user profile.")));
+ }
+
+ return "
$picture
";
+ }
+ }
+}
+
+function theme_user_profile($account) {
+ $output = "
\n";
+ $output .= theme('user_picture', $account);
+ $output .= form_item(t('Name'), $account->name);
+ $output .= implode("\n", module_invoke_all('user', 'view', '', $account));
+ $output .= form_item(t('Member for'), format_interval(time() - $account->created));
+
+ if (user_access("administer users")) {
+ $output .= form_item(t("Administration"), l(t("edit account"), "admin/user/edit/$account->uid"));
+ }
+
+ $output .= "
\n";
+
+ return $output;
+}
+
function theme_user_list($items, $title = NULL) {
return theme("item_list", $items, $title);
}
@@ -595,7 +661,7 @@ function user_login($edit = array(), $msg = "") {
watchdog('user', "session opened for '$user->name'");
// update the user table timestamp noting user has logged in
- db_query("UPDATE {users} SET timestamp = '%d' WHERE uid = '%s'", time(), $user->uid);
+ db_query("UPDATE {users} SET changed = '%d' WHERE uid = '%s'", time(), $user->uid);
user_module_invoke("login", $edit, $user);
@@ -685,7 +751,7 @@ function user_logout() {
*/
session_destroy();
- module_invoke_all('user', "logout", NULL, $user);
+ module_invoke_all('user', 'logout', NULL, $user);
unset($user);
}
@@ -884,7 +950,15 @@ function user_edit($edit = array()) {
else if ($edit['mail'] && db_num_rows(db_query("SELECT uid FROM {users} WHERE uid != '$user->uid' AND LOWER(mail) = LOWER('%s')", $edit['mail'])) > 0) {
$error = t("The e-mail address '%s' is already taken.", array("%s" => $edit['mail']));
}
- else if ($user->uid) {
+ else {
+ /*
+ ** If required, validate the picture.
+ */
+
+ if ($file = file_check_upload('picture')) {
+ $error = user_validate_picture($file, $edit, $user);
+ }
+
/*
** If required, check that proposed passwords match. If so,
** add new password to $edit.
@@ -922,7 +996,7 @@ function user_edit($edit = array()) {
foreach (module_list() as $module) {
if (module_hook($module, 'user')) {
- $result = module_invoke($module, 'user', "edit_validate", $edit, $user);
+ $result = module_invoke($module, 'user', 'validate', $edit, $user);
}
if (is_array($result)) {
$data = array_merge($data, $result);
@@ -940,7 +1014,7 @@ function user_edit($edit = array()) {
$user = user_save($user, array_merge($edit, $data));
- drupal_set_message(t("your user information changes have been saved."));
+ drupal_set_message(t('your user information changes have been saved.'));
}
}
}
@@ -953,15 +1027,25 @@ function user_edit($edit = array()) {
$edit = object2array($user);
}
- $output = form_textfield(t("Username"), 'name', $edit['name'], 30, 55, t("Your full name or your preferred username: only letters, numbers and spaces are allowed."));
- $output .= form_textfield(t("E-mail address"), "mail", $edit['mail'], 30, 55, t("Insert a valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail."));
- $output .= form_item(t("Password"), "
", t("Enter your new password twice if you want to change your current password or leave it blank if you are happy with your current password."));
- $output = form_group(t('Account information'), $output);
+ $group = form_textfield(t("Username"), 'name', $edit['name'], 30, 55, t("Your full name or your preferred username: only letters, numbers and spaces are allowed."));
+ $group .= form_textfield(t("E-mail address"), "mail", $edit['mail'], 30, 55, t("Insert a valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail."));
+ $group .= form_item(t("Password"), "
", t("Enter your new password twice if you want to change your current password or leave it blank if you are happy with your current password."));
+ $output = form_group(t('Account information'), $group);
+
+ if (variable_get('user_pictures', 0)) {
+ $group = '';
+ if (file_exists($user->picture)) {
+ $group .= '
';
+ }
+ $group .= form_file(t('Upload picture or picture'), 'picture', 48, t("Your virtual face or picture. Maximum dimensions are %dimensions and the maximum size is %size kB.", array("%dimensions" => variable_get('user_picture_dimensions', "85x85"), "%size" => variable_get('user_picture_file_size', "30"))) ." ". variable_get('user_picture_guidelines', ''));
+ $output .= form_group(t('Picture'), $group);
+ }
+
$output .= _user_profile($edit, $user);
$output .= form_submit(t("Save user information"));
$output = form($output, "post", 0, array("enctype" => "multipart/form-data"));
- // the "enctype" attribute is required to upload files such as avatars
+ // the "enctype" attribute is required to upload files such as pictures
}
else {
$output = user_login();
@@ -973,7 +1057,7 @@ function user_edit($edit = array()) {
function _user_profile($edit, $account) {
foreach (module_list() as $module) {
- if ($data = module_invoke($module, 'user', 'edit_form', $edit, $account)) {
+ if ($data = module_invoke($module, 'user', 'edit', $edit, $account)) {
foreach ($data as $title => $form) {
$groups[$title] .= $form;
}
@@ -991,37 +1075,27 @@ function _user_profile($edit, $account) {
function user_view($uid = 0) {
global $user;
- if (!$uid) {
- $uid = $user->uid;
- }
-
- if ($user->uid && $user->uid == $uid) {
- $output = form_item(t("Name"), "$user->name ($user->init)");
- $output .= form_item(t("E-mail address"), $user->mail, t("Please note that only you can see your own e-mail address - it is not publicly visible."));
-
- $output .= implode("\n", module_invoke_all('user', "view_private", "", $user));
-
- print theme('page', $output, $user->name);
- }
- else if ($uid && $account = user_load(array('uid' => $uid, "status" => 1))) {
- $output = form_item(t("Name"), $account->name);
-
- $output .= implode("\n", module_invoke_all('user', "view_public", "", $account));
-
- if (user_access("administer users")) {
- $output .= form_item(t("Administration"), l(t("edit account"), "admin/user/edit/$account->uid"));
+ if ($uid == 0) {
+ if ($user->uid) {
+ print theme('page', theme('user_profile', $user), $user->name);
}
+ else {
+ $output = user_login();
+ if (variable_get("user_register", 1)) {
+ $output .= user_register();
+ }
+ $output .= user_pass();
- print theme('page', $output, $account->name);
+ print theme('page', $output, t("User login"));
+ }
}
else {
- $output = user_login();
- if (variable_get("user_register", 1)) {
- $output .= user_register();
+ if ($account = user_load(array('uid' => $uid, "status" => 1))) {
+ print theme('page', theme('user_profile', $account), $account->name);
+ }
+ else {
+ drupal_not_found();
}
- $output .= user_pass();
-
- print theme('page', $output, t("User login"));
}
}
@@ -1124,6 +1198,20 @@ function user_settings() {
$group .= form_textarea(t("Body of password recovery e-mail"), "user_mail_pass_body", _user_mail_text("pass_body"), 70, 10, t("Customize the body of the forgotten password e-mail.") ." ". t("Available variables are:") ." %username, %site, %password, %uri, %uri_brief, %mailto, %login_uri, %edit_uri.");
$output .= form_group(t("User email settings"), $group);
+ // picture settings:
+ if (!file_check_directory(file_create_path(variable_get('user_picture_path', 'pictures')))) {
+ $error = theme('error', t('The picture directory does not exist, or is not writable.'));
+ }
+
+ $group = form_radios(t('Picture support'), 'user_pictures', variable_get('user_pictures', 0), array(t('Disabled'), t('Enabled')), t('Enable picture support.'));
+ $group .= form_textfield(t("Picture image path"), 'user_picture_path', variable_get('user_picture_path', "pictures"), 45, 255, t("Subdirectory in the directory '%dir' where pictures will be stored.", array('%dir' => variable_get('file_directory_path', 'files') . FILE_SEPARATOR)) . $error);
+ $group .= form_textfield(t('Default picture'), 'user_picture_default', variable_get('user_picture_default', ''), 45, 255, t('URL of picture to display for users with no custom picture selected. Leave blank for none.'));
+ $group .= form_textfield(t("Picture maximum dimensions"), 'user_picture_dimensions', variable_get('user_picture_dimensions', "85x85"), 10, 10, t("Maximum dimensions for pictures."));
+ $group .= form_textfield(t("Picture maximum file size"), 'user_picture_file_size', variable_get('user_picture_file_size', "30"), 10, 10, t("Maximum file size for pictures, in kB."));
+ $group .= form_textarea(t("Picture guidelines"), 'user_picture_guidelines', variable_get('user_picture_guidelines', ''), 70, 4, t("This text is displayed at the picture upload form in addition to the default guidelines. It's useful for helping or instructing your users."));
+
+ $output .= form_group(t('Pictures'), $group);
+
// "Who's online" block settings
$period = drupal_map_assoc(array(30, 60, 120, 180, 300, 600, 900, 1800, 2700, 3600, 5400, 7200, 10800, 21600, 43200, 86400), "format_interval");
$group = form_select(t("User activity"), "user_block_seconds_online", variable_get("user_block_seconds_online", 900), $period, t("Affects \"Who's online\" block. A user is considered online for this long after they have last viewed a page."));
@@ -1270,7 +1358,7 @@ function user_admin_perm($edit = array()) {
** Compile permission array:
*/
- $perms = module_invoke_all("perm");
+ $perms = module_invoke_all('perm');
asort($perms);
/*
@@ -1376,7 +1464,7 @@ function user_admin_edit($edit = array()) {
if ($op == t("Save account")) {
foreach (module_list() as $module) {
if (module_hook($module, 'user')) {
- $result = module_invoke($module, 'user', "edit_validate", $edit, $account);
+ $result = module_invoke($module, 'user', 'validate', $edit, $account);
}
if (is_array($result)) {
$data = array_merge($data, $result);
@@ -1401,6 +1489,14 @@ function user_admin_edit($edit = array()) {
$error = t("The e-mail address '%s' is already taken.", array("%s" => $edit['mail']));
}
+ /*
+ ** If required, validate the picture.
+ */
+
+ if ($file = file_check_upload('picture')) {
+ $error = user_validate_picture($file, $edit, $account);
+ }
+
/*
** If required, check that proposed passwords match. If so,
** add new password to $edit.
@@ -1429,7 +1525,7 @@ function user_admin_edit($edit = array()) {
db_query("DELETE FROM {users} WHERE uid = %d", $account->uid);
db_query("DELETE FROM {authmap} WHERE uid = %d", $account->uid);
drupal_set_message(t("the account has been deleted."));
- module_invoke_all('user', "delete", $account, $user);
+ module_invoke_all('user', 'delete', $account, $user);
}
else {
$error = t("Failed to delete account: the account has to be blocked first.");
@@ -1445,14 +1541,24 @@ function user_admin_edit($edit = array()) {
** Display user form:
*/
- $output .= form_item(t("User ID"), $account->uid);
- $output .= form_textfield(t("Username"), 'name', $account->name, 30, 55, t("Your full name or your preferred username: only letters, numbers and spaces are allowed."));
- $output .= form_textfield(t("E-mail address"), "mail", $account->mail, 30, 55, t("Insert a valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail."));
- $output .= form_item(t("Password"), "
", t("Enter a new password twice if you want to change the current password for this user or leave it blank if you are happy with the current password."));
- $output .= form_radios(t("Status"), "status", $account->status, array(t("Blocked"), t("Active")));
- $output .= form_radios(t("Role"), "rid", $account->rid, user_roles(1));
+ $group = form_item(t("User ID"), $account->uid);
+ $group .= form_textfield(t("Username"), 'name', $account->name, 30, 55, t("Your full name or your preferred username: only letters, numbers and spaces are allowed."));
+ $group .= form_textfield(t("E-mail address"), "mail", $account->mail, 30, 55, t("Insert a valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail."));
+ $group .= form_item(t("Password"), "
", t("Enter a new password twice if you want to change the current password for this user or leave it blank if you are happy with the current password."));
+ $group .= form_radios(t("Status"), "status", $account->status, array(t("Blocked"), t("Active")));
+ $group .= form_radios(t("Role"), "rid", $account->rid, user_roles(1));
+
+ $output = form_group(t('Account information'), $group);
+
+ if (variable_get('user_pictures', 0)) {
+ $group = '';
+ if (file_exists($account->picture)) {
+ $group .= '
';
+ }
+ $group .= form_file(t('Upload picture or picture'), 'picture', 48, t("Maximum dimensions are %dimensions and the maximum size is %size kB.", array("%dimensions" => variable_get('user_picture_dimensions', "85x85"), "%size" => variable_get('user_picture_file_size', "30"))));
+ $output .= form_group(t('Picture'), $group);
+ }
- $output = form_group(t('Account information'), $output);
$output .= _user_profile($edit, $account);
$output .= form_submit(t("Save account"));
@@ -1473,16 +1579,16 @@ function user_admin_account() {
array("data" => t("username"), "field" => "u.name"),
array("data" => t("status"), "field" => "u.status"),
array("data" => t("role"), "field" => "u.rid"),
- array("data" => t("last access"), "field" => "u.timestamp", "sort" => "desc"),
+ array("data" => t("last access"), "field" => "u.changed", "sort" => "desc"),
t("operations")
);
- $sql = "SELECT u.uid, u.name, u.status, u.timestamp, r.name AS rolename FROM {role} r INNER JOIN {users} u ON r.rid = u.rid WHERE uid != 0";
+ $sql = "SELECT u.uid, u.name, u.status, u.changed, r.name AS rolename FROM {role} r INNER JOIN {users} u ON r.rid = u.rid WHERE uid != 0";
$sql .= tablesort_sql($header);
$result = pager_query($sql, 50);
$status = array(t("blocked"), t("active"));
while ($account = db_fetch_object($result)) {
- $rows[] = array($account->uid, format_name($account), $status[$account->status], $account->rolename, format_date($account->timestamp, "small"), l(t("edit account"), "admin/user/edit/$account->uid"));
+ $rows[] = array($account->uid, format_name($account), $status[$account->status], $account->rolename, format_date($account->changed, "small"), l(t("edit account"), "admin/user/edit/$account->uid"));
}
$pager = theme("pager", NULL, 50, 0, tablesort_pager());
@@ -1692,18 +1798,14 @@ function user_help($section = "admin/help#user") {
function julia_user(\$type, \$edit, &\$user) {
// What type of registration action are we taking?
switch (\$type) {
- case t(\"view_public\"):
- // when others look at user data
+ case t(\"view\"):
return form_item(\"Favorite Ingredient\", \$user->julia_favingredient);
- case t(\"view_private\"):
- // when user tries to view his own user page.
- return form_item(\"Favorite Ingredient\", \$user->julia_favingredient);
- case t(\"edit_form\"):
+ case t(\"edit\"):
// when user tries to edit his own user page.
return form_textfield(\"Favorite Ingredient\", \"julia_favingredient\",
\$user->julia_favingredient, 50, 65,
\"Tell everyone your secret spice\");
- case t(\"edit_validate\"): // Make sure the data they edited is \"valid\".
+ case t(\"validate\"): // Make sure the data they edited is \"valid\".
return user_save(\$user, array(\"julia_favingredient\" => \$edit[\"julia_favingredient\"]));
}
}
diff --git a/modules/user/user.module b/modules/user/user.module
index 68d25921a2d..1dbc33dafe4 100644
--- a/modules/user/user.module
+++ b/modules/user/user.module
@@ -78,12 +78,13 @@ function user_save($account, $array = array()) {
$query .= "data = '%s', ";
$v[] = serialize($data);
- db_query("UPDATE {users} SET $query timestamp = %d WHERE uid = %d", array_merge($v, array(time(), $account->uid)));
+ db_query("UPDATE {users} SET $query changed = %d WHERE uid = %d", array_merge($v, array(time(), $account->uid)));
$user = user_load(array('uid' => $account->uid));
}
else {
- $array['timestamp'] = time();
+ $array['created'] = time();
+ $array['changed'] = time();
$array['uid'] = db_next_id("{users}_uid");
foreach ($array as $key => $value) {
@@ -112,11 +113,11 @@ function user_save($account, $array = array()) {
$user = user_load(array('name' => $array['name']));
- module_invoke_all('user', "insert", $array, $user);
+ module_invoke_all('user', 'insert', $array, $user);
}
foreach ($array as $key => $value) {
- if (substr($key, 0, 4) == "auth") {
+ if (substr($key, 0, 4) == 'auth') {
$authmaps[$key] = $value;
}
}
@@ -136,7 +137,7 @@ function user_validate_name($name) {
if (!$name) return t("You must enter a username.");
if (substr($name, 0, 1) == ' ') return t("The username cannot begin with a space.");
if (substr($name, -1) == ' ') return t("The username cannot end with a space.");
- if (ereg(" ", $name)) return t("The username cannot contain multiple spaces in a row.");
+ if (ereg(' ', $name)) return t("The username cannot contain multiple spaces in a row.");
if (ereg('[^ [:alnum:]@_.-]', $name)) return t("The username contains an illegal character.");
if (ereg('@', $name) && !eregi('@([0-9a-z](-?[0-9a-z])*.)+[a-z]{2}([zmuvtg]|fo|me)?$', $name)) return t("The username is not a valid authentication ID.");
if (strlen($name) > 56) return t("The username '%name' is too long: it must be less than 56 characters.", array("%name" => $name));
@@ -149,6 +150,35 @@ function user_validate_mail($mail) {
}
}
+function user_validate_picture($file, &$edit, $user) {
+
+ // initialize the picture:
+ $edit['picture'] = $user->picture;
+
+ // check that uploaded file is an image, with a maximum file size and maximum height/width
+ $extension = strtolower(strrchr($file->name, "."));
+ $size = getimagesize($file->path);
+ list($maxwidth, $maxheight) = explode("x", variable_get('user_picture_dimensions', "85x85"));
+
+ if ((!in_array($size[2], array(1, 2, 3))) || (!in_array($extension, array(".gif", ".jpg", ".png", ".jpeg")))) {
+ $error = t("The uploaded file was not an image.");
+ }
+ else if ($file->size > (variable_get('user_picture_file_size', "30") * 1000)) {
+ $error = t("The uploaded image is too large; the maximum file size is %a kB.", array("%a" => variable_get('user_picture_file_size', "30")));
+ }
+ else if ($size[0] > $maxwidth || $size[1] > $maxheight) {
+ $error = t("The uploaded image is too large; the maximum dimensions are %a pixels.", array("%a" => variable_get('user_picture_dimensions', "85x85")));
+ }
+ else if ($file = file_save_upload('picture', variable_get('user_picture_path', "pictures") . FILE_SEPARATOR .'picture-'. $user->uid . $extension, 1)) {
+ $edit['picture'] = $file->path;
+ }
+ else {
+ $error = t("Failed to upload the picture image; the '%directory' directory doesn't exist.", array("%directory" => variable_get('user_picture_path', "pictures")));
+ }
+
+ return $error;
+}
+
function user_validate_authmap($account, $authname, $module) {
$result = db_query("SELECT COUNT(*) from {authmap} WHERE uid != %d AND authname = '%s'", $account->uid, $authname);
if (db_result($result) > 0) {
@@ -281,7 +311,7 @@ function user_fields() {
}
else {
// Make sure we return the default fields at least
- $fields = array('uid', 'name', 'pass', "mail", "mode", "sort", "threshold", "theme", "signature", "timestamp", "status", "timezone", "language", "init", "data", "rid");
+ $fields = array('uid', 'name', 'pass', "mail", "picture", "mode", "sort", "threshold", "theme", "signature", "created", "changed", "status", "timezone", "language", "init", "data", "rid");
}
}
@@ -428,6 +458,42 @@ function user_block($op = "list", $delta = 0) {
}
}
+function theme_user_picture($account) {
+ if (variable_get('user_pictures', 0)) {
+ if ($account->picture && file_exists($account->picture)) {
+ $picture = file_create_url($account->picture);
+ }
+ else if (variable_get('user_picture_default', '')) {
+ $picture = variable_get('user_picture_default', '');
+ }
+
+ if ($picture) {
+ $picture = "
$account->name ? $account->name : t(variable_get("anonymous", "Anonymous")))) . "\" />";
+ if ($account->uid) {
+ $picture = l($picture, "user/view/$account->uid", array("title" => t("View user profile.")));
+ }
+
+ return "
$picture
";
+ }
+ }
+}
+
+function theme_user_profile($account) {
+ $output = "
\n";
+ $output .= theme('user_picture', $account);
+ $output .= form_item(t('Name'), $account->name);
+ $output .= implode("\n", module_invoke_all('user', 'view', '', $account));
+ $output .= form_item(t('Member for'), format_interval(time() - $account->created));
+
+ if (user_access("administer users")) {
+ $output .= form_item(t("Administration"), l(t("edit account"), "admin/user/edit/$account->uid"));
+ }
+
+ $output .= "
\n";
+
+ return $output;
+}
+
function theme_user_list($items, $title = NULL) {
return theme("item_list", $items, $title);
}
@@ -595,7 +661,7 @@ function user_login($edit = array(), $msg = "") {
watchdog('user', "session opened for '$user->name'");
// update the user table timestamp noting user has logged in
- db_query("UPDATE {users} SET timestamp = '%d' WHERE uid = '%s'", time(), $user->uid);
+ db_query("UPDATE {users} SET changed = '%d' WHERE uid = '%s'", time(), $user->uid);
user_module_invoke("login", $edit, $user);
@@ -685,7 +751,7 @@ function user_logout() {
*/
session_destroy();
- module_invoke_all('user', "logout", NULL, $user);
+ module_invoke_all('user', 'logout', NULL, $user);
unset($user);
}
@@ -884,7 +950,15 @@ function user_edit($edit = array()) {
else if ($edit['mail'] && db_num_rows(db_query("SELECT uid FROM {users} WHERE uid != '$user->uid' AND LOWER(mail) = LOWER('%s')", $edit['mail'])) > 0) {
$error = t("The e-mail address '%s' is already taken.", array("%s" => $edit['mail']));
}
- else if ($user->uid) {
+ else {
+ /*
+ ** If required, validate the picture.
+ */
+
+ if ($file = file_check_upload('picture')) {
+ $error = user_validate_picture($file, $edit, $user);
+ }
+
/*
** If required, check that proposed passwords match. If so,
** add new password to $edit.
@@ -922,7 +996,7 @@ function user_edit($edit = array()) {
foreach (module_list() as $module) {
if (module_hook($module, 'user')) {
- $result = module_invoke($module, 'user', "edit_validate", $edit, $user);
+ $result = module_invoke($module, 'user', 'validate', $edit, $user);
}
if (is_array($result)) {
$data = array_merge($data, $result);
@@ -940,7 +1014,7 @@ function user_edit($edit = array()) {
$user = user_save($user, array_merge($edit, $data));
- drupal_set_message(t("your user information changes have been saved."));
+ drupal_set_message(t('your user information changes have been saved.'));
}
}
}
@@ -953,15 +1027,25 @@ function user_edit($edit = array()) {
$edit = object2array($user);
}
- $output = form_textfield(t("Username"), 'name', $edit['name'], 30, 55, t("Your full name or your preferred username: only letters, numbers and spaces are allowed."));
- $output .= form_textfield(t("E-mail address"), "mail", $edit['mail'], 30, 55, t("Insert a valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail."));
- $output .= form_item(t("Password"), "
", t("Enter your new password twice if you want to change your current password or leave it blank if you are happy with your current password."));
- $output = form_group(t('Account information'), $output);
+ $group = form_textfield(t("Username"), 'name', $edit['name'], 30, 55, t("Your full name or your preferred username: only letters, numbers and spaces are allowed."));
+ $group .= form_textfield(t("E-mail address"), "mail", $edit['mail'], 30, 55, t("Insert a valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail."));
+ $group .= form_item(t("Password"), "
", t("Enter your new password twice if you want to change your current password or leave it blank if you are happy with your current password."));
+ $output = form_group(t('Account information'), $group);
+
+ if (variable_get('user_pictures', 0)) {
+ $group = '';
+ if (file_exists($user->picture)) {
+ $group .= '
';
+ }
+ $group .= form_file(t('Upload picture or picture'), 'picture', 48, t("Your virtual face or picture. Maximum dimensions are %dimensions and the maximum size is %size kB.", array("%dimensions" => variable_get('user_picture_dimensions', "85x85"), "%size" => variable_get('user_picture_file_size', "30"))) ." ". variable_get('user_picture_guidelines', ''));
+ $output .= form_group(t('Picture'), $group);
+ }
+
$output .= _user_profile($edit, $user);
$output .= form_submit(t("Save user information"));
$output = form($output, "post", 0, array("enctype" => "multipart/form-data"));
- // the "enctype" attribute is required to upload files such as avatars
+ // the "enctype" attribute is required to upload files such as pictures
}
else {
$output = user_login();
@@ -973,7 +1057,7 @@ function user_edit($edit = array()) {
function _user_profile($edit, $account) {
foreach (module_list() as $module) {
- if ($data = module_invoke($module, 'user', 'edit_form', $edit, $account)) {
+ if ($data = module_invoke($module, 'user', 'edit', $edit, $account)) {
foreach ($data as $title => $form) {
$groups[$title] .= $form;
}
@@ -991,37 +1075,27 @@ function _user_profile($edit, $account) {
function user_view($uid = 0) {
global $user;
- if (!$uid) {
- $uid = $user->uid;
- }
-
- if ($user->uid && $user->uid == $uid) {
- $output = form_item(t("Name"), "$user->name ($user->init)");
- $output .= form_item(t("E-mail address"), $user->mail, t("Please note that only you can see your own e-mail address - it is not publicly visible."));
-
- $output .= implode("\n", module_invoke_all('user', "view_private", "", $user));
-
- print theme('page', $output, $user->name);
- }
- else if ($uid && $account = user_load(array('uid' => $uid, "status" => 1))) {
- $output = form_item(t("Name"), $account->name);
-
- $output .= implode("\n", module_invoke_all('user', "view_public", "", $account));
-
- if (user_access("administer users")) {
- $output .= form_item(t("Administration"), l(t("edit account"), "admin/user/edit/$account->uid"));
+ if ($uid == 0) {
+ if ($user->uid) {
+ print theme('page', theme('user_profile', $user), $user->name);
}
+ else {
+ $output = user_login();
+ if (variable_get("user_register", 1)) {
+ $output .= user_register();
+ }
+ $output .= user_pass();
- print theme('page', $output, $account->name);
+ print theme('page', $output, t("User login"));
+ }
}
else {
- $output = user_login();
- if (variable_get("user_register", 1)) {
- $output .= user_register();
+ if ($account = user_load(array('uid' => $uid, "status" => 1))) {
+ print theme('page', theme('user_profile', $account), $account->name);
+ }
+ else {
+ drupal_not_found();
}
- $output .= user_pass();
-
- print theme('page', $output, t("User login"));
}
}
@@ -1124,6 +1198,20 @@ function user_settings() {
$group .= form_textarea(t("Body of password recovery e-mail"), "user_mail_pass_body", _user_mail_text("pass_body"), 70, 10, t("Customize the body of the forgotten password e-mail.") ." ". t("Available variables are:") ." %username, %site, %password, %uri, %uri_brief, %mailto, %login_uri, %edit_uri.");
$output .= form_group(t("User email settings"), $group);
+ // picture settings:
+ if (!file_check_directory(file_create_path(variable_get('user_picture_path', 'pictures')))) {
+ $error = theme('error', t('The picture directory does not exist, or is not writable.'));
+ }
+
+ $group = form_radios(t('Picture support'), 'user_pictures', variable_get('user_pictures', 0), array(t('Disabled'), t('Enabled')), t('Enable picture support.'));
+ $group .= form_textfield(t("Picture image path"), 'user_picture_path', variable_get('user_picture_path', "pictures"), 45, 255, t("Subdirectory in the directory '%dir' where pictures will be stored.", array('%dir' => variable_get('file_directory_path', 'files') . FILE_SEPARATOR)) . $error);
+ $group .= form_textfield(t('Default picture'), 'user_picture_default', variable_get('user_picture_default', ''), 45, 255, t('URL of picture to display for users with no custom picture selected. Leave blank for none.'));
+ $group .= form_textfield(t("Picture maximum dimensions"), 'user_picture_dimensions', variable_get('user_picture_dimensions', "85x85"), 10, 10, t("Maximum dimensions for pictures."));
+ $group .= form_textfield(t("Picture maximum file size"), 'user_picture_file_size', variable_get('user_picture_file_size', "30"), 10, 10, t("Maximum file size for pictures, in kB."));
+ $group .= form_textarea(t("Picture guidelines"), 'user_picture_guidelines', variable_get('user_picture_guidelines', ''), 70, 4, t("This text is displayed at the picture upload form in addition to the default guidelines. It's useful for helping or instructing your users."));
+
+ $output .= form_group(t('Pictures'), $group);
+
// "Who's online" block settings
$period = drupal_map_assoc(array(30, 60, 120, 180, 300, 600, 900, 1800, 2700, 3600, 5400, 7200, 10800, 21600, 43200, 86400), "format_interval");
$group = form_select(t("User activity"), "user_block_seconds_online", variable_get("user_block_seconds_online", 900), $period, t("Affects \"Who's online\" block. A user is considered online for this long after they have last viewed a page."));
@@ -1270,7 +1358,7 @@ function user_admin_perm($edit = array()) {
** Compile permission array:
*/
- $perms = module_invoke_all("perm");
+ $perms = module_invoke_all('perm');
asort($perms);
/*
@@ -1376,7 +1464,7 @@ function user_admin_edit($edit = array()) {
if ($op == t("Save account")) {
foreach (module_list() as $module) {
if (module_hook($module, 'user')) {
- $result = module_invoke($module, 'user', "edit_validate", $edit, $account);
+ $result = module_invoke($module, 'user', 'validate', $edit, $account);
}
if (is_array($result)) {
$data = array_merge($data, $result);
@@ -1401,6 +1489,14 @@ function user_admin_edit($edit = array()) {
$error = t("The e-mail address '%s' is already taken.", array("%s" => $edit['mail']));
}
+ /*
+ ** If required, validate the picture.
+ */
+
+ if ($file = file_check_upload('picture')) {
+ $error = user_validate_picture($file, $edit, $account);
+ }
+
/*
** If required, check that proposed passwords match. If so,
** add new password to $edit.
@@ -1429,7 +1525,7 @@ function user_admin_edit($edit = array()) {
db_query("DELETE FROM {users} WHERE uid = %d", $account->uid);
db_query("DELETE FROM {authmap} WHERE uid = %d", $account->uid);
drupal_set_message(t("the account has been deleted."));
- module_invoke_all('user', "delete", $account, $user);
+ module_invoke_all('user', 'delete', $account, $user);
}
else {
$error = t("Failed to delete account: the account has to be blocked first.");
@@ -1445,14 +1541,24 @@ function user_admin_edit($edit = array()) {
** Display user form:
*/
- $output .= form_item(t("User ID"), $account->uid);
- $output .= form_textfield(t("Username"), 'name', $account->name, 30, 55, t("Your full name or your preferred username: only letters, numbers and spaces are allowed."));
- $output .= form_textfield(t("E-mail address"), "mail", $account->mail, 30, 55, t("Insert a valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail."));
- $output .= form_item(t("Password"), "
", t("Enter a new password twice if you want to change the current password for this user or leave it blank if you are happy with the current password."));
- $output .= form_radios(t("Status"), "status", $account->status, array(t("Blocked"), t("Active")));
- $output .= form_radios(t("Role"), "rid", $account->rid, user_roles(1));
+ $group = form_item(t("User ID"), $account->uid);
+ $group .= form_textfield(t("Username"), 'name', $account->name, 30, 55, t("Your full name or your preferred username: only letters, numbers and spaces are allowed."));
+ $group .= form_textfield(t("E-mail address"), "mail", $account->mail, 30, 55, t("Insert a valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail."));
+ $group .= form_item(t("Password"), "
", t("Enter a new password twice if you want to change the current password for this user or leave it blank if you are happy with the current password."));
+ $group .= form_radios(t("Status"), "status", $account->status, array(t("Blocked"), t("Active")));
+ $group .= form_radios(t("Role"), "rid", $account->rid, user_roles(1));
+
+ $output = form_group(t('Account information'), $group);
+
+ if (variable_get('user_pictures', 0)) {
+ $group = '';
+ if (file_exists($account->picture)) {
+ $group .= '
';
+ }
+ $group .= form_file(t('Upload picture or picture'), 'picture', 48, t("Maximum dimensions are %dimensions and the maximum size is %size kB.", array("%dimensions" => variable_get('user_picture_dimensions', "85x85"), "%size" => variable_get('user_picture_file_size', "30"))));
+ $output .= form_group(t('Picture'), $group);
+ }
- $output = form_group(t('Account information'), $output);
$output .= _user_profile($edit, $account);
$output .= form_submit(t("Save account"));
@@ -1473,16 +1579,16 @@ function user_admin_account() {
array("data" => t("username"), "field" => "u.name"),
array("data" => t("status"), "field" => "u.status"),
array("data" => t("role"), "field" => "u.rid"),
- array("data" => t("last access"), "field" => "u.timestamp", "sort" => "desc"),
+ array("data" => t("last access"), "field" => "u.changed", "sort" => "desc"),
t("operations")
);
- $sql = "SELECT u.uid, u.name, u.status, u.timestamp, r.name AS rolename FROM {role} r INNER JOIN {users} u ON r.rid = u.rid WHERE uid != 0";
+ $sql = "SELECT u.uid, u.name, u.status, u.changed, r.name AS rolename FROM {role} r INNER JOIN {users} u ON r.rid = u.rid WHERE uid != 0";
$sql .= tablesort_sql($header);
$result = pager_query($sql, 50);
$status = array(t("blocked"), t("active"));
while ($account = db_fetch_object($result)) {
- $rows[] = array($account->uid, format_name($account), $status[$account->status], $account->rolename, format_date($account->timestamp, "small"), l(t("edit account"), "admin/user/edit/$account->uid"));
+ $rows[] = array($account->uid, format_name($account), $status[$account->status], $account->rolename, format_date($account->changed, "small"), l(t("edit account"), "admin/user/edit/$account->uid"));
}
$pager = theme("pager", NULL, 50, 0, tablesort_pager());
@@ -1692,18 +1798,14 @@ function user_help($section = "admin/help#user") {
function julia_user(\$type, \$edit, &\$user) {
// What type of registration action are we taking?
switch (\$type) {
- case t(\"view_public\"):
- // when others look at user data
+ case t(\"view\"):
return form_item(\"Favorite Ingredient\", \$user->julia_favingredient);
- case t(\"view_private\"):
- // when user tries to view his own user page.
- return form_item(\"Favorite Ingredient\", \$user->julia_favingredient);
- case t(\"edit_form\"):
+ case t(\"edit\"):
// when user tries to edit his own user page.
return form_textfield(\"Favorite Ingredient\", \"julia_favingredient\",
\$user->julia_favingredient, 50, 65,
\"Tell everyone your secret spice\");
- case t(\"edit_validate\"): // Make sure the data they edited is \"valid\".
+ case t(\"validate\"): // Make sure the data they edited is \"valid\".
return user_save(\$user, array(\"julia_favingredient\" => \$edit[\"julia_favingredient\"]));
}
}
diff --git a/themes/xtemplate/default/xtemplate.css b/themes/xtemplate/default/xtemplate.css
index cc42447dcff..fcf8d4f0855 100644
--- a/themes/xtemplate/default/xtemplate.css
+++ b/themes/xtemplate/default/xtemplate.css
@@ -222,7 +222,7 @@ table {
font-size: 0.8em;
padding: 1.5em;
}
-.node .avatar {
+.node .picture {
border: 1px solid #ddd;
float: right;
margin: 0.5em;
@@ -242,7 +242,7 @@ table {
float: right;
color: red;
}
-.comment .avatar {
+.comment .picture {
border: 1px solid #abc;
float: right;
margin: 0.5em;
diff --git a/themes/xtemplate/default/xtemplate.xtmpl b/themes/xtemplate/default/xtemplate.xtmpl
index b6c74d22bbc..a1e0e72ac74 100644
--- a/themes/xtemplate/default/xtemplate.xtmpl
+++ b/themes/xtemplate/default/xtemplate.xtmpl
@@ -56,9 +56,9 @@
-
-
{avatar}
-
+
+ {picture}
+
@@ -75,9 +75,9 @@