variable_get(USERPOINTS_TRANS_UCPOINTS, 'Points'),
'!points' => variable_get(USERPOINTS_TRANS_LCPOINTS, 'points'),
'!point' => variable_get(USERPOINTS_TRANS_LCPOINT, 'point'),
'!Uncategorized' => variable_get(USERPOINTS_TRANS_UNCAT, 'Uncategorized'),
);
}
return $trans;
}
/*
* Purpose: Returns an array of possible transaction statuses
*/
function userpoints_txn_status() {
return array(
USERPOINTS_TXN_STATUS_APPROVED => t('Approved'),
USERPOINTS_TXN_STATUS_PENDING => t('Pending'),
USERPOINTS_TXN_STATUS_DECLINED => t('Declined'),
);
}
/**
* Implementation of hook_help().
*/
function userpoints_help($section) {
switch ($section) {
case 'admin/settings/userpoints':
$output = t('Configure userpoints moderation and branding translation', userpoints_translation());
break;
case 'admin/help#userpoints':
$output = t('Users earn !points as they post nodes, comments, and vote on nodes', userpoints_translation());
}
return $output;
}
/**
* Implementation of hook_menu().
*/
function userpoints_menu() {
$items = array();
$items['admin/settings/userpoints'] = array(
'title' => '!Points settings',
'title arguments' => userpoints_translation(),
'page callback' => 'drupal_get_form',
'page arguments' => array('userpoints_admin_settings'),
'access arguments' => array(USERPOINTS_PERM_ADMIN),
'type' => MENU_NORMAL_ITEM
);
$items['admin/user/userpoints'] = array(
'title' => '!Points',
'title arguments' => userpoints_translation(),
'description' => 'Manage !points',
'page callback' => 'userpoints_admin_points',
'access arguments' => array(USERPOINTS_PERM_ADMIN)
);
$items['admin/user/userpoints/list'] = array(
'title' => 'List',
'title arguments' => userpoints_translation(),
'description' => 'List users by points',
'access arguments' => array(USERPOINTS_PERM_VIEW),
'type' => MENU_DEFAULT_LOCAL_TASK,
'weight' => -2,
);
$items['admin/user/userpoints/moderate'] = array(
'title' => 'Moderation',
'title arguments' => userpoints_translation(),
'description' => 'Review points in moderation',
'page callback' => 'userpoints_admin_points',
'access arguments' => array(USERPOINTS_PERM_ADMIN),
'type' => MENU_LOCAL_TASK,
'weight' => -1,
);
$items['admin/user/userpoints/add'] = array(
'title' => 'Add',
'description' => 'Admin add/delete userpoints',
'page callback' => 'drupal_get_form',
'page arguments' => array('userpoints_admin_txn'),
'access arguments' => array(USERPOINTS_PERM_ADMIN),
'type' => MENU_LOCAL_TASK,
'weight' => 0,
);
$items['admin/user/userpoints/edit'] = array(
'title' => 'Edit',
'page callback' => 'drupal_get_form',
'page arguments' => array('userpoints_admin_txn'),
'access arguments' => array(USERPOINTS_PERM_ADMIN),
'type' => MENU_CALLBACK
);
$items['admin/user/userpoints/approve'] = array(
'title' => 'Approve Userpoints',
'page callback' => 'userpoints_admin_approve',
'access arguments' => array(USERPOINTS_PERM_ADMIN),
'type' => MENU_CALLBACK
);
$items['admin/user/userpoints/decline'] = array(
'title' => 'Approve Userpoints',
'page callback' => 'userpoints_admin_approve',
'access arguments' => array(USERPOINTS_PERM_ADMIN),
'type' => MENU_CALLBACK
);
$items['userpoints'] = array(
'title' => 'Users by !points',
'title arguments' => userpoints_translation(),
'page callback' => 'userpoints_list_users',
'access' => array(USERPOINTS_PERM_VIEW),
'type' => MENU_NORMAL_ITEM,
);
$items['myuserpoints'] = array(
'title' => 'My !points',
'title arguments' => userpoints_translation(),
'page callback' => 'userpoints_my_userpoints',
'access callback' => 'userpoints_access_my_points',
'type' => MENU_NORMAL_ITEM
);
return $items;
}
/**
* Checks if user can access their points - used via hook_menu().
*
* @return true if user has permissions to view userpoints and if the user is logged in
*/
function userpoints_access_my_points() {
global $user;
return (user_access(USERPOINTS_PERM_VIEW) && user_is_logged_in());
}
/**
* Implementation of hook_perm().
*/
function userpoints_perm() {
return array(USERPOINTS_PERM_VIEW, USERPOINTS_PERM_ADMIN);
}
/**
* Implementation of hook_theme().
*/
function userpoints_theme() {
$themes = array();
$themes['userpoints_list_users'] = array(
'arguments' => array(
'header',
'rows',
'tid',
'pager_limit',
),
);
$themes['userpoints_list_users_header'] = array(
);
$themes['userpoints_list_users_row'] = array(
'arguments' => array(
'row'
),
);
$themes['userpoints_my_userpoints'] = array(
'arguments' => array(
'args',
'header',
'rows',
),
);
return $themes;
}
/**
* menu callback for settings form.
*/
function userpoints_admin_settings() {
$form = array();
$group = 'status';
$form[$group] = array(
'#type' => 'fieldset',
'#title' => t('Moderation'),
'#collapsible' => TRUE,
'#collapsed' => TRUE,
'#weight' => -1,
);
$form[$group][USERPOINTS_POINTS_MODERATION] = array(
'#type' => 'radios',
'#title' => t('Transaction status'),
'#default_value' => variable_get(USERPOINTS_POINTS_MODERATION, 0),
'#options' => array(t('Approved'), t('Moderated')),
'#description' => t('Select whether all !points should be approved automatically, or moderated, and require admin approval', userpoints_translation()),
);
$group = 'renaming';
$form[$group] = array(
'#type' => 'fieldset',
'#collapsible' => TRUE,
'#collapsed' => TRUE,
'#title' => t('Points branding'),
);
$form[$group][USERPOINTS_TRANS_UCPOINTS] = array(
'#type' => 'textfield',
'#title' => t('Word to use in the interface for the upper case plural word !Points', userpoints_translation()),
'#default_value' => variable_get(USERPOINTS_TRANS_UCPOINTS, 'Points'),
'#size' => 20,
'#maxlength' => 20,
);
$form[$group][USERPOINTS_TRANS_LCPOINTS] = array(
'#type' => 'textfield',
'#title' => t('Word to use in the interface for the lower case plural word !points', userpoints_translation()),
'#default_value' => variable_get(USERPOINTS_TRANS_LCPOINTS, 'points'),
'#size' => 20,
'#maxlength' => 20,
);
$form[$group][USERPOINTS_TRANS_LCPOINT] = array(
'#type' => 'textfield',
'#title' => t('Word to use in the interface for the lower case singular word !point', userpoints_translation()),
'#default_value' => variable_get(USERPOINTS_TRANS_LCPOINT, 'point'),
'#size' => 20,
'#maxlength' => 20,
);
$form[$group][USERPOINTS_TRANS_UNCAT] = array(
'#type' => 'textfield',
'#title' => t('Word to use for the uncategorized category'),
'#default_value' => variable_get(USERPOINTS_TRANS_UNCAT, 'Uncategorized'),
'#size' => 20,
'#maxlength' => 20,
);
$group = "Points expiration";
$form[$group] = array(
'#type' => 'fieldset',
'#collapsible' => TRUE,
'#collapsed' => TRUE,
'#title' => t('!Points expiration', userpoints_translation()),
'#description' => t('These settings affect new points only, they are not retroactive!
Point expiration depends upon cron.
'),
);
$form[$group][USERPOINTS_EXPIREAFTER_DATE] = array(
'#type' => 'select',
'#title' => t('Expire !points after', userpoints_translation()),
'#description' => t('Once points have been obtained by the user
they will expire according to this setting'),
'#options' => expiry_dates(),
'#default_value' => variable_get(USERPOINTS_EXPIREAFTER_DATE, NULL),
);
/**
* If the expiration date is earlier than today
* new points will last forever. Although this may be desirable
* it could also be an oversight so we'll display a message
* to the administrator
*
*/
$warning="";
if (userpoints_date_to_timestamp(variable_get(USERPOINTS_EXPIREON_DATE, array('day' => 1, 'month' => 1, 'year' => 1900))) < time()) {
$warning = '
'. t('This setting will not take affect, date must be in the future') .'';
}
$form[$group][USERPOINTS_EXPIREON_DATE] = array(
'#type' => 'date',
'#title' => t('Expire !points on this date', userpoints_translation()),
'#description' => t('Once points have been obtained by the user they will
last until this date. This setting overrides the
"Expire after setting" above'. $warning),
'#default_value' => variable_get(USERPOINTS_EXPIREON_DATE, array('day' => 1, 'month' => 1, 'year' => 1980)),
);
$form[$group][USERPOINTS_EXPIRY_DESCRIPTION] = array(
'#type' => 'textarea',
'#title' => t('Expiration entry description'),
'#description' => t('A negating expiration entry is made to expire
points leaving the original entry intact
(e.g. original points + expiration points = 0).
When the expiration entry is made this description will
be placed on the entry. This is useful so the users will
know what happened to their point balance. In crafting
your message you can use the following variables.
!points = The name used in branding
above (also use !Points and !point)
!operation = Original operation that granted the points
!description = Original description for the point
!txn_id Original transaction ID
!date = Date of the original entry'),
'#default_value' => variable_get(USERPOINTS_EXPIRY_DESCRIPTION, ''),
);
$group = "misc";
$form[$group] = array(
'#type' => 'fieldset',
'#collapsible' => TRUE,
'#collapsed' => TRUE,
'#title' => t('Messages'),
'#description' => t('Control the behavior of messages users see. '),
);
$form[$group][USERPOINTS_DISPLAY_MESSAGE] = array(
'#type' => 'radios',
'#title' => t('Display message'),
'#default_value' => variable_get(USERPOINTS_DISPLAY_MESSAGE, 1),
'#options' => array(0 => t('No'), 1 => t('Yes')),
'#description' => t('Determines if a message should be displayed whenever !points are awarded/substracted ', userpoints_translation()),
);
$group = "reports";
$form[$group] = array(
'#type' => 'fieldset',
'#collapsible' => TRUE,
'#collapsed' => TRUE,
'#title' => t('Report Settings'),
'#description' => t(''),
);
$form[$group][USERPOINTS_REPORT_LIMIT] = array(
'#type' => 'select',
'#title' => t('Transactions per page'),
'#default_value' => variable_get(USERPOINTS_REPORT_LIMIT, 10),
'#options' => array(10 => 10, 20 => 20, 30 => 30, 40 => 40, 50 => 50, 100 => 100),
'#description' => t('Limits the number of transactions displayed per page'),
);
$form[$group][USERPOINTS_REPORT_DISPLAYZERO] = array(
'#type' => 'radios',
'#title' => t('Display zero !point users?', userpoints_translation()),
'#default_value' => variable_get(USERPOINTS_REPORT_DISPLAYZERO, 1),
'#options' => array(t('No'), t('Yes')),
'#description' => t('If set to "No" users with zero !points will not be displayed in the reports ', userpoints_translation()),
);
$form[$group][USERPOINTS_REPORT_USERCOUNT] = array(
'#type' => 'select',
'#title' => t('Users per page'),
'#default_value' => variable_get(USERPOINTS_REPORT_USERCOUNT, 30),
'#options' => array(10 => 10, 20 => 20, 30 => 30, 40 => 40, 50 => 50, 100 => 100),
'#description' => t('When listing !points by user limit how many users are displayed on a single page', userpoints_translation()),
);
/* Categories will only appear if the taxonomy module is enabled as
* the module is required for this functionality but not necessarily
* a requirement for the module.
*/
if (module_exists('taxonomy')) {
$group = 'category';
$form[$group] = array(
'#type' => 'fieldset',
'#collapsible' => TRUE,
'#collapsed' => TRUE,
'#title' => t('!Points Categorization', userpoints_translation()),
);
$form[$group][USERPOINTS_CATEGORY_DEFAULT_TID] = array(
'#type' => 'select',
'#title' => t('Default Category'),
'#default_value' => variable_get(USERPOINTS_CATEGORY_DEFAULT_TID, NULL),
'#options' => userpoints_get_categories(),
'#description' => t('By default all points are assigned to this category. You can modify what categories are available by modifying the Userpoints taxonomy',
array('!url' => url('admin/content/taxonomy/'. variable_get(USERPOINTS_CATEGORY_DEFAULT_VID, '')))),
);
}
$form['setting'] = module_invoke_all('userpoints', 'setting');
return system_settings_form($form);
}
/**
* @param uid: user id of the user to get or lose the points
*
* @return number of current points in that user's account
*/
function userpoints_get_current_points($uid = NULL, $tid = NULL) {
if (!$uid) {
global $user;
$uid = $user->uid;
}
if (!$tid) {
$tid = userpoints_get_default_tid();
}
elseif ($tid == 'all') {
return (int)db_result(db_query('SELECT SUM(points) FROM {userpoints} WHERE uid = %d', $uid));
}
return (int)db_result(db_query('SELECT points FROM {userpoints} WHERE uid = %d AND tid = %d', $uid, $tid));
}
/**
* @param uid: user id of the user to get or lose the points
*
* @return number of max points in that user's account
*/
function userpoints_get_max_points($uid = NULL, $tid = NULL) {
if (!$uid) {
global $user;
$uid = $user->uid;
}
if (!$tid) {
$tid = userpoints_get_default_tid();
}
elseif ($tid == 'all') {
return (int)db_result(db_query('SELECT SUM(max_points) FROM {userpoints} WHERE uid = %d', $uid));
}
return (int)db_result(db_query('SELECT max_points FROM {userpoints} WHERE uid = %d AND tid = %d', $uid, $tid));
}
/**
* @param $params(array) or (int)
* if (int) assumed to be points for current user
* Accepts an array of keyed variables and parameters
* 'points' => # of points (int) (required)
* 'moderate' => TRUE/FALSE
* 'uid' => $user->uid
* 'operation' => 'published' 'moderated' etc.
* 'tid' => 'category ID'
* 'expirydate' => timestamp or 0, 0 = non-expiring; NULL = site default
* 'description' => 'description'
* 'reference' => reserved for module specific use
* 'display' => whether or not to display "points awarded" message
* 'txn_id' => Transaction ID of points, If present an UPDATE is performed
* 'entity_id' => ID of an entity in the Database. ex. $node->id or $user->uid
* 'entity_type' => string of the entity type. ex. 'node' or 'user' NOT 'node-content-custom'
*
* @return array with status and reason.
* 'status' => FALSE when no action is take, TRUE when points are credited or debited
* 'reason' => (string) error message to indicate reason for failure
*/
function userpoints_userpointsapi($params) {
//Test for the existence of parameters and set defaults if necessary
if (!isset($params['txn_id'])) {
//If a txn_id is passed in we'll do an UPDATE thus the std check don't apply
if (is_numeric($params)) {
$points = $params;
$params = array();
$params['points'] = $points;
unset($points);
}
if (!is_array($params)) {
//has to be an array to continue
return array(
'status' => false,
'reason' => 'Parameters did not properly form as an array,
this is an internal module error.
',
);
}
if (!isset($params['uid'])) {
global $user;
$params['uid'] = $user->uid;
}
if (!isset($params['operation'])) {
$params['operation'] = NULL;
}
if (!isset($params['description'])) {
$params['description'] = NULL;
}
if (!isset($params['reference'])) {
$params['reference'] = NULL;
}
if (!isset($params['display'])) {
$params['display'] = NULL;
}
if (!isset($params['moderate'])) {
//if not passed then site default is used
$params['status'] = variable_get(USERPOINTS_POINTS_MODERATION, 0);
}
else {
if ($params['moderate'] == true) {
$params['status'] = 1;
}
else {
$params['status'] = 0;
}
}
if (!isset($params['tid']) || !is_numeric($params['tid'])) {
//if not passed then site default is used
$params['tid'] = variable_get(USERPOINTS_CATEGORY_DEFAULT_TID, NULL);
}
if (!isset($params['entity_id'])) {
$params['entity_id'] = NULL;
}
if (!isset($params['entity_type'])) {
$params['entity_type'] = NULL;
}
// anonymous users do not get points, and there have to be points to process
if (($params['uid'] == 0 || $params['points'] == 0)) {
return array(
'status' => false,
'reason' => 'uid or points = 0. Anonymous users do not get points
and there must be points to process.
',
);
}
}
else {
//We have a txn_id so we can look up some user information
$sql = "SELECT uid from {userpoints_txn} WHERE txn_id = %d";
$params['uid'] = db_result(db_query($sql, $params['txn_id']));
} //if txn_id
// Load the user object that will be awarded the points
$account = user_load(array('uid' => $params['uid']));
// Call the _userpoints hook, and stop if one of them returns FALSE
$rc = module_invoke_all('userpoints', 'points before', $params['points'], $account->uid, $params['event']);
foreach ($rc as $key => $value) {
if ($value == FALSE) {
// Do not process the points
return array(
'status' => false,
'reason' => t('%key returned false from the hook_userpoints points before call', array('%key' => $key)),
);
}
}
if ($params['points'] < 0) {
$msg = t('lost');
}
elseif ($params['status'] == 2) {
//points have been declined
$msg = t('was declined');
}
else {
$msg = t('earned');
}
$ret = _userpoints_transaction($params);
if ($ret == false) {
return array(
'status' => false,
'reason' => 'transaction failed in _userpoints_transaction, this is an internal module error',
);
}
if ($params['status'] == 1) {
$mesg = (t('User %uname %op %pointsvalue !points, pending administrator approval.',
array_merge(userpoints_translation(), array(
'%uname' => $account->name,
'%op' => $msg,
'%pointsvalue' => abs($params['points']),
'%total' => userpoints_get_current_points($params['uid'], $params['tid'])
))));
}
else {
$mesg = (t('User %uname %op %pointsvalue !points! Total now is %total points.',
array_merge(userpoints_translation(), array(
'%uname' => $account->name,
'%op' => $msg,
'%pointsvalue' => abs($params['points']),
'%total' => userpoints_get_current_points($params['uid'], $params['tid'])
))));
} //if $params['status']
if ($mesg && ($params['display'] || ($params['display'] === null && variable_get(USERPOINTS_DISPLAY_MESSAGE, 1) == 1))) {
drupal_set_message($mesg);
}
// Call the _userpoints hook to allow modules to act after points are awarded
module_invoke_all('userpoints', 'points after', $params['points'], $account->uid, $params['operation']);
return array(
'status' => true,
);
}
/*
* Adds the points to the txn table
* PRIVATE FUNCTION use userpoints_userpointsapi!
*/
function _userpoints_transaction(&$params) {
//Check, again, for a properly formed array
if (!is_array($params)) {
return false;
}
if (!isset($params['txn_id'])) {
//If a txn_id is preset we UPDATE the record instead of adding one
//the standard checks don't apply
if (!is_numeric($params['points'])) {
return false;
}
if (!isset($params['uid'])) {
global $user;
$params['uid'] = $user->uid;
//there must be a UID, anonymous does not receive points
if (!$params['uid'] > 0) {
return false;
}
}
if (!isset($params['moderate'])) {
//if not passed then site default is used
$params['status'] = variable_get(USERPOINTS_POINTS_MODERATION, 0);
}
else {
if ($params['moderate'] == true) {
$params['status'] = 1;
}
else {
$params['status'] = 0;
}
}
if (!isset($params['operation'])) {
$params['operation'] = NULL;
}
if (!isset($params['description'])) {
$params['description'] = NULL;
}
if (!isset($params['reference'])) {
$params['reference'] = NULL;
}
if (!isset($params['tid']) || !is_numeric($params['tid'])) {
$params['tid'] = variable_get(USERPOINTS_CATEGORY_DEFAULT_TID, NULL);
}
elseif ($params['tid'] == 0) {
//tid with 0 are uncategorized and are set to NULL
//this is a backwards compatibilty issue
$params['tid'] = NULL;
}
if (!isset($params['expirydate'])) {
$params['expirydate'] = userpoints_get_default_expiry_date();
}
if (!isset($params['expired'])) {
$params['expired'] = NULL;
}
if (!isset($params['parent_txn_id'])) {
$params['parent_txn_id'] = NULL;
}
if (!isset($params['entity_id'])) {
$params['entity_id'] = NULL;
}
if (!isset($params['entity_type'])) {
$params['entity_type'] = NULL;
}
} // if txn_id
if (is_numeric($params['txn_id'])) {
//A transaction ID was passed in so we'll update the transaction
$result = db_query("SELECT txn_id, uid, approver_uid, points,
time_stamp, status, operation, description, reference, expirydate, expired,
parent_txn_id, tid, entity_id, entity_type
FROM {userpoints_txn}
WHERE txn_id = %d",
$params['txn_id']);
$txn = db_fetch_array($result);
foreach ($txn as $key => $value) {
if (isset($params[$key])) {
$arr[] = $key .' = \''. $params[$key] .'\'';
}
else {
$params[$key] = $value;
}
}
db_query('UPDATE {userpoints_txn} SET '. implode(', ', $arr) .'
WHERE txn_id = %d',
$params['txn_id']
);
_userpoints_update_cache($params);
}
else {
$ret = db_query("INSERT INTO {userpoints_txn}
(uid, points, time_stamp, status, operation, description,
reference, expirydate, expired, parent_txn_id, tid, entity_id, entity_type)
VALUES (%d, %d, %d, %d, '%s', '%s', '%s', %d, %d, %d, %d, %d, '%s')",
$params['uid'],
$params['points'],
time(),
$params['status'],
$params['operation'],
$params['description'],
$params['reference'],
$params['expirydate'],
$params['expired'],
$params['parent_txn_id'],
$params['tid'],
$params['entity_id'],
$params['entity_type']
);
if ($params['status'] != true && $ret != false) {
_userpoints_update_cache($params);
}
}
return TRUE;
} //function userpoints_transaction
/*
* Update the caching table
*/
function _userpoints_update_cache(&$params) {
if ( $params['status'] != 0 || $params['expired'] == 1) {
//Only update the cache for fully approved non-expired points
return false;
}
if (!isset($params['tid'])) {
$params['tid'] = NULL;
}
// Calculate the current points based upon the tid
$current_points = (int)$params['points'] + userpoints_get_current_points($params['uid'], $params['tid']);
//Grab the user's maximum points to preserve it
$max_points = db_result(db_query('SELECT max_points FROM {userpoints} WHERE uid = %d AND tid = %d',
$params['uid'], $params['tid']));
if ($params['points'] > 0) {
//points are greater than zero, update their max_points
$max_points = (int)$params['points'] + (int)$max_points;
}
// insert or update the userpoints caching table with the user's current points
if (_userpoints_user_exists($params['uid'], $params['tid'])) {
db_query("UPDATE {userpoints}
SET points = %d, max_points = %d, last_update = %d
WHERE uid = %d AND tid = %d",
$current_points,
$max_points,
time(),
$params['uid'],
$params['tid']
);
}
else {
$result = db_query("INSERT INTO {userpoints}
(uid, points, max_points, last_update, tid)
VALUES (%d, %d, %d, %d, %d )",
$params['uid'],
$current_points,
$max_points,
time(),
$params['tid']
);
}
unset($params);
}
/* Purpose: Determines the correct default expiration date
* Returns: timestamp
*/
function userpoints_get_default_expiry_date() {
$expirydate = userpoints_date_to_timestamp(variable_get(USERPOINTS_EXPIREON_DATE, NULL));
if ($expirydate < time()) {
$expirydate = variable_get(USERPOINTS_EXPIREAFTER_DATE, NULL);
if ($expirydate) {
$expirydate = time() + $expirydate;
}
}
return $expirydate;
} //userpoints_get_default_expiry_date
/*
* Purpose: Checks to ensure that a user exists corresponding to a category
* @param $uid User ID to check for existence of points for the user
* @param $tid taxonomy id of the category to limit to, if omitted
* if the use has points in any category the return is true
* Returns : true if user found, falase otherwise
*/
function _userpoints_user_exists($uid, $tid = NULL) {
if ( is_numeric($tid) ) {
return (int)db_result(
db_query('SELECT COUNT(uid)
FROM {userpoints}
WHERE uid = %d AND tid = %d ',
$uid, $tid));
}
else {
return (int)db_result(
db_query('SELECT COUNT(uid)
FROM {userpoints}
WHERE uid = %d',
$uid ));
}
}
function userpoints_user($op, &$edit, &$account, $category = '') {
switch ($op) {
case 'delete':
// The user is being deleted, delete all traces in userpoints and txn tables
db_query('DELETE FROM {userpoints} WHERE uid = %d', $account->uid);
db_query('DELETE FROM {userpoints_txn} WHERE uid = %d', $account->uid);
break;
case 'view':
// Get the points for the user
$points = userpoints_get_current_points($account->uid);
if (user_access(USERPOINTS_PERM_ADMIN)) {
$points = l($points, 'admin/user/userpoints/add/'. $account->uid, array('title' => t('Manage points')));
}
if (user_access(USERPOINTS_PERM_VIEW)) {
$disp_points[] = array(
'title' => t('User !points', userpoints_translation()),
'value' => $points,
);
return array(t('!Points', userpoints_translation()) => $disp_points);
}
break;
}
}
function userpoints_admin_manage() {
$tid = arg(4);
$cat_count = count(userpoints_get_categories());
$header = array(
array('data' => t('User'), 'field' => 'uid', 'sort' => 'desc'),
array('data' => t('Time stamp'), 'field' => 'time_stamp'),
array('data' => t('!Points', userpoints_translation()), 'field' => 'points'),
array('data' => t('Operation'), 'field' => 'operation'),
array('data' => t('Category'), 'field' => 'cat'),
array('data' => t('Operation')),
);
$sql = "SELECT p.txn_id, p.uid, p.time_stamp, p.points, p.operation, p.status,
p.entity_type, p.entity_id, t.name as cat
FROM {userpoints_txn} p
LEFT JOIN {term_data} t ON p.tid = t.tid
WHERE p.status = %d";
//Check for filtering
if (is_numeric($tid) && $tid == 0) {
$sql .= " AND (p.tid IS NULL OR p.tid = '')";
$cat = t('!Uncategorized', userpoints_translation());
}
elseif (is_numeric($tid)) {
$sql .= " AND p.tid = %d";
$cat = db_result(db_query("SELECT name from {term_data} WHERE tid = %d", $tid));
}
else {
$cat = t('All');
}
//Set the title of the page
drupal_set_title(t($cat) ." ". t("!points", userpoints_translation()));
$sql .= tablesort_sql($header);
$pager_limit = variable_get(USERPOINTS_REPORT_USERCOUNT, 30);
$result = pager_query($sql, $pager_limit, 0, NULL, USERPOINTS_TXN_STATUS_PENDING, $tid);
while ($data = db_fetch_object($result)) {
$user = user_load(array('uid' => $data->uid));
if (!$data->cat) {
$data->cat = t('!Uncategorized', userpoints_translation());
}
$operation = module_invoke_all('userpoints', 'entity_type', $data);
if (!$operation) {
switch ($data->entity_type) {
case 'node' :
$node = node_load($data->entity_id);
if ($node) {
$operation = l($data->operation, 'node/'. $node->nid, array('title' => $node->title));
}
else {
$operation = $data->operation;
}
break;
case 'comment' :
if (module_exists('comment')) {
//We have to load the comment to get the nid for the comment
$comment = _comment_load($data->entity_id);
if ($comment) {
$operation = l($data->operation, 'node/'. $comment->nid, array('title' => $comment->subject), NULL, 'comment-'. $comment->cid);
}
else {
$operation = $data->operation;
}
}
break;
default:
$operation = $data->operation;
}
}
$rows[] = array(
array('data' => theme('username', $user)),
array('data' => format_date($data->time_stamp, 'custom', 'Y-m-d H:i')),
array('data' => $data->points, 'align' => 'right'),
array('data' => $operation),
array('data' => $data->cat),
array('data' => l('approve', "admin/user/userpoints/approve/$data->txn_id") .
' '. l('decline', "admin/user/userpoints/decline/$data->txn_id") .
' '. l('edit', "admin/user/userpoints/edit/$data->txn_id")
),
);
}
if (!$rows) {
//no points in moderation
$rows[] = array(array('data' => t('No !points awaiting moderation', userpoints_translation()),
'colspan' => 6, 'align' => 'center')
); //$rows[]
}
if ($cat_count > 1) {
$output = drupal_get_form('userpoints_filter_cat_select', 'admin/user/userpoints/moderate/', arg(4));
$output .= theme('table', $header, $rows);
$output .= theme('pager', NULL, $pager_limit, 0);
}
else {
$output = theme('table', $header, $rows);
$output .= theme('pager', NULL, $pager_limit, 0);
}
return $output;
}
/*
* Purpose: Approves moderated points
*/
function userpoints_admin_approve() {
$operation = arg(3);
$txn_id = (int)arg(4);
return drupal_get_form('userpoints_confirm_approve', $operation, $txn_id);
}
function userpoints_confirm_approve($operation, $txn_id) {
$form = array(
'operation' => array(
'#type' => 'value',
'#value' => $operation,
),
'txn_id' => array(
'#type' => 'value',
'#value' => $txn_id,
),
);
return confirm_form(
$form,
t('Are you sure you want to @op txn @txn_id', array('@op' => $operation, '@txn_id' => $txn_id)),
'admin/user/userpoints/moderate'
);
}
function userpoints_confirm_approve_submit($form, &$form_state) {
global $user;
$form_values = $form_state['values'];
switch ($form_state['clicked_button']['#value']) {
case 'approve':
$status = USERPOINTS_TXN_STATUS_APPROVED;
break;
case 'decline':
$status = USERPOINTS_TXN_STATUS_DECLINED;
break;
default :
return false;
}
$params = array(
'txn_id' => $form_values['txn_id'],
'approver_uid' => $user->uid,
'status' => $status,
);
userpoints_userpointsapi($params);
$form_state['redirect'] = 'admin/user/userpoints/moderate';
}
function userpoints_admin_txn($form_state) {
global $user;
$mode = arg(3);
$timestamp = format_date(time(), 'custom', 'Y-m-d H:i O');
if ($mode == 'edit' && arg(4)) {
$txn_id = (int)arg(4);
$result = db_query('SELECT * FROM {userpoints_txn} WHERE txn_id = %d', $txn_id);
$txn = db_fetch_object($result);
$timestamp = format_date($txn->time_stamp, 'custom', 'Y-m-d H:i O');
$txn_user = user_load(array('uid' => $txn->uid));
}
elseif ($mode == 'add' && arg(4)) {
$uid = (int)arg(4);
$txn_user = user_load(array('uid' => $uid));
}
$form['txn_user'] = array(
'#type' => 'textfield',
'#title' => t('User Name'),
'#size' => 30,
'#maxlength' => 60,
'#default_value' => $txn_user->name,
'#autocomplete_path' => 'user/autocomplete',
'#description' => t('User Name for the user you want the points to affect'),
);
$form['points'] = array(
'#type' => 'textfield',
'#title' => t('Points'),
'#size' => 10,
'#maxlength' => 10,
'#default_value' => $txn->points,
'#description' => t('Number of points to add/subtract from the user. For example, 25 (to add points) or -25 (to subtract points).'),
);
$form['time_stamp'] = array(
'#type' => 'textfield',
'#title' => t('Date/Time'),
'#default_value' => $timestamp,
'#size' => 30,
'#maxlength' => 30,
'#description' => t('Date and time of this transaction, in the form YYYY-MM-DD HH:MM +ZZZZ'),
);
if ($txn->txn_id) {
if ($txn->expirydate > 0) {
$expirydate = format_date($txn->expirydate, 'custom', 'Y-m-d H:i O');
}
}
else {
//If we're not editing we use site defaults
$expirydate = userpoints_get_default_expiry_date();
if ($expirydate) {
$expirydate = format_date($expirydate, 'custom', 'Y-m-d H:i O');
}
}
$form['expirydate'] = array(
'#type' => 'textfield',
'#title' => t('Expiration date'),
'#default_value' => $expirydate,
'#size' => 30,
'#maxlength' => 30,
'#description' => t('Date and time to expire these points, in the form YYYY-MM-DD HH:MM +ZZZZ') .
'
'. t('Leave blank for non-expiring points'),
);
if (module_exists('taxonomy')) {
$form['tid'] = array(
'#type' => 'select',
'#title' => t('Category'),
'#default_value' => variable_get(USERPOINTS_CATEGORY_DEFAULT_TID, 0),
'#options' => userpoints_get_categories(),
'#description' => t('Category to apply these points to'),
);
}
$form['reference'] = array(
'#type' => 'textfield',
'#title' => t('Reference'),
'#default_value' => $txn->reference,
'#size' => 30,
'#maxlength' => 128,
'#description' => t('Enter optional reference for this transaction. This field will be indexed and searchable.'),
);
$form['description'] = array(
'#type' => 'textarea',
'#title' => t('Description'),
'#default_value' => $txn->description,
'#width' => 70,
'#lines' => 5,
'#description' => t('Enter an optional description for this transaction, such as the reason it is created.'),
);
switch ($mode) {
case 'add':
$form['approver_uid'] = array(
'#type' => 'hidden',
'#value' => $user->uid,
);
$form['operation'] = array(
'#type' => 'hidden',
'#value' => 'admin',
);
$form['status'] = array(
'#type' => 'hidden',
'#value' => USERPOINTS_TXN_STATUS_PENDING,
);
$form['mode'] = array(
'#type' => 'hidden',
'#value' => $mode,
);
break;
case 'edit':
$form['txn_user']['#disabled'] = true;
unset($form['txn_user']['#autocomplete_path']);
$form['txn_uid'] = array(
'#type' => 'value',
'#value' => $txn->uid,
);
$form['txn_id'] = array(
'#type' => 'value',
'#value' => $txn_id,
);
$form['approver_uid'] = array(
'#type' => 'textfield',
'#description' => t('Approver ID'),
'#default_value' => $txn->approver_uid,
'#size' => 10,
'#maxlength' => 7,
'#description' => t('The user ID of the person who approved this transaction. 0 means not yet approved.'),
);
$form['operation'] = array(
'#type' => 'textfield',
'#description' => t('Operation'),
'#default_value' => $txn->operation,
'#size' => 20,
'#maxlength' => 20,
'#description' => t('The operation type for this transaction. Normally, it is "admin".'),
);
$form['status'] = array(
'#title' => t('Approval status'),
'#type' => 'radios',
'#options' => userpoints_txn_status(),
'#description' => t('Approval status of the transaction.'),
'#default_value' => $txn->status,
);
break;
}
$form['mode'] = array(
'#type' => 'hidden',
'#default_value' => $mode
);
$form['submit'] = array(
'#type' => 'submit',
'#value' => t('Save'),
);
return $form;
}
function userpoints_admin_txn_submit($form, &$form_state) {
if ($form['form_id']['#value'] != 'userpoints_admin_txn') {
return;
}
$form_values = $form_state['values'];
$txn_user = user_load(array('name' => $form_values['txn_user']));
switch ($form_values['mode']) {
case 'add':
$params = array(
'points' => $form_values['points'],
'uid' => $txn_user->uid,
'operation' => 'admin',
'description' => $form_values['description'],
'reference' => $form_values['reference'],
'tid' => $form_values['tid'],
);
if ($form_values['expirydate']) {
//Check for the existence of an expirydate
$params['expirydate'] = strtotime($form_values['expirydate']);
}
userpoints_userpointsapi($params);
break;
case 'edit':
if ($form_values['expirydate']) {
$expirydate = strtotime($$form_values['expirydate']);
}
$params = array(
'uid' => $form_values['txn_uid'],
'approver_id' => $form_values['approver_uid'],
'points' => $form_values['points'],
'time_stamp' => strtotime($form_values['time_stamp']),
'operation' => $form_values['operation'],
'description' => $form_values['description'],
'reference' => $form_values['reference'],
'status' => $form_values['status'],
'expirydate' => $expirydate,
'txn_id' => $form_values['txn_id']
);
userpoints_userpointsapi($params);
}
$form_state['redirect'] = 'admin/user/userpoints';
}
/*
* Provides an administrative Interface for point listing, moderation and adding
*/
function userpoints_admin_points() {
$tid = arg(3);
$cat_count = count(userpoints_get_categories());
$sql = "SELECT p.uid, u.name, p.points, p.tid, t.name as cat
FROM {userpoints} p INNER JOIN {users} u USING (uid)
LEFT JOIN {term_data} t ON p.tid = t.tid
";
//Check for filtering
if ( $tid == 0) {
$sql .= "WHERE p.tid = 0";
$cat = t('!Uncategorized', userpoints_translation());
}
elseif (is_numeric($tid)) {
$sql .= "WHERE p.tid = %d";
$cat = db_result(db_query("SELECT name from {term_data} WHERE tid = %d", $tid));
}
else {
$cat = t('All');
}
drupal_set_title(t($cat) ." ". t("!points", userpoints_translation()));
$sql_cnt = "SELECT COUNT(DISTINCT(uid))
FROM {userpoints}
WHERE tid = %d
";
if (variable_get(USERPOINTS_REPORT_DISPLAYZERO, 1) == 0 ) {
//The user would NOT like to see users with zero points
$sql .= " AND p.points <> 0";
$sql_cnt .= " AND points <> 0";
}
$sql .= " GROUP BY p.uid, u.name, p.points, p.tid, t.name";
$header = array(
array('data' => t('User'), 'field' => 'u.name'),
array('data' => t('Category'), 'field' => 't.name'),
array('data' => t('!Points', userpoints_translation()), 'field' => 'p.points', 'sort' => 'desc'),
);
$sql .= tablesort_sql($header);
$pager_limit = variable_get(USERPOINTS_REPORT_USERCOUNT, 30);
$result = pager_query($sql, $pager_limit, 0, $sql_cnt, $tid);
while ($data = db_fetch_object($result)) {
if (!$data->cat) {
$data->cat = t('!Uncategorized', userpoints_translation());
}
$rows[] = array(
array('data' => theme('username', $data) ." ". l("(details)", "myuserpoints/$data->uid")),
array('data' => $data->cat, 'align' => 'right'),
array('data' => $data->points, 'align' => 'right'),
);
}
//If there is only one category there is no sense in display the category filter dropdown
if ($cat_count > 1) {
$output = drupal_get_form('userpoints_filter_cat_select', 'admin/user/userpoints/', arg(3));
$output .= theme('table', $header, $rows);
$output .= theme('pager', NULL, $pager_limit, 0);
}
else {
$output = theme('table', $header, $rows);
$output .= theme('pager', NULL, $pager_limit, 0);
}
return $output;
}
/*
* Purpose: List the users and their point totals by all or by category
* Returns: HTML from the theme function
*/
function userpoints_list_users() {
$tid = arg(1);
$sql = "SELECT p.uid, u.name, p.points, p.tid, t.name as cat
FROM {userpoints} p INNER JOIN {users} u USING (uid)
LEFT JOIN {term_data} t ON p.tid = t.tid
";
//Check for filtering
if (is_numeric($tid)) {
if ($tid > 0) {
$sql .= "WHERE p.tid = %d";
$cat = db_result(db_query("SELECT name from {term_data} WHERE tid = %d", $tid));
}
else {
$sql .= "WHERE p.tid = %d";
$cat = t('!Uncategorized', userpoints_translation());
}
}
else {
$cat = t('All');
}
$sql_cnt = "SELECT COUNT(DISTINCT(uid))
FROM {userpoints}
WHERE tid = %d
";
if (variable_get(USERPOINTS_REPORT_DISPLAYZERO, 1) == 0 ) {
//The user would NOT like to see users with zero points
$sql .= " AND p.points <> 0";
$sql_cnt .= " AND points <> 0";
}
$sql .= " GROUP BY p.uid, u.name, p.points, p.tid, t.name";
$header = theme('userpoints_list_users_header');
$sql .= tablesort_sql($header);
$pager_limit = variable_get(USERPOINTS_REPORT_USERCOUNT, 30);
$result = pager_query($sql, $pager_limit, 0, $sql_cnt, $tid);
while ($data = db_fetch_object($result)) {
$rows[] = theme('userpoints_list_users_row', $data);
}
drupal_set_title(t($cat) ." ". t("!points", userpoints_translation()));
return theme('userpoints_list_users', $header, $rows, $tid, $pager_limit);
}
/*
* Purpose: themes the output of users by points page accessible at /userpoints
* individual rows are themed with theme_userpoints_list_users_rows
* Returns: HTML
*/
function theme_userpoints_list_users($header, &$rows, &$tid, &$pager_limit) {
//If there is only one category there is no sense in display the category filter dropdown
if ( count(userpoints_get_categories()) > 1) {
$output = drupal_get_form('userpoints_filter_cat_select', 'userpoints/', $tid);
$output .= theme('table', $header, $rows);
$output .= theme('pager', NULL, $pager_limit, 0);
}
else {
$output = theme('table', $header, $rows);
$output .= theme('pager', NULL, $pager_limit, 0);
}
return $output;
}
/*
* Purpose: themes the header of the table on the "user by points" page accessible at /userpoints
* Returns: An array suitable for use with tablesort_sql
*/
function theme_userpoints_list_users_header() {
return array(
array('data' => t('User'), 'field' => 'u.name'),
array('data' => t('Category'), 'field' => 't.name'),
array('data' => t('!Points', userpoints_translation()), 'field' => 'p.points', 'sort' => 'desc'),
);
}
/*
* Purpose: themes the output of a single row of the "user by points" page at /userpoints
* Returns: array for a single row suitable for inclusion with theme_table
*/
function theme_userpoints_list_users_row(&$row) {
global $user;
if (!$row->cat) {
$row->cat = t('!Uncategorized', userpoints_translation());
}
if ($user->uid == $row->uid) {
$details = " ". l("(details)", "myuserpoints");
}
return array(
array('data' => theme('username', $row) . $details),
array('data' => $row->cat, 'align' => 'right'),
array('data' => $row->points, 'align' => 'right'),
);
}
/*
* Purpose: Provides a dropdown to filter by category
*/
function userpoints_filter_cat_select($path, $tid) {
$current_cat = url($path . $tid);
$form = array();
$formname = 'catselect';
$sql = "SELECT DISTINCT p.tid, t.name
FROM {userpoints_txn} p
LEFT JOIN {term_data} t on p.tid = t.tid";
$cats = userpoints_get_categories();
$options = array();
$options[url($path)] = t('Display all');
foreach ($cats as $key => $value) {
$options[url($path . $key)] = $value;
}
$form['catselect'] = array(
'#type' => 'select',
'#name' => $formname,
'#id' => $formname,
'#title' => t('Filter by category'),
'#default_value' => $current_cat,
'#options' => $options,
'#multiple' => false,
'#required' => false,
'#attributes' => array('onChange' => "top.location.href=document.getElementById('$formname').options[document.getElementById('$formname').selectedIndex].value"),
);
return $form;
} //userpoints_list_users_cat_select
function userpoints_block($op = 'list', $delta = 0, $edit = array()) {
global $user;
switch ($op) {
case 'list':
$blocks[-1]['info'] = t('User\'s !points', userpoints_translation());
//Grab a list of the available terms
$terms = userpoints_get_categories();
foreach ($terms as $key => $value) {
$blocks[$key]['info'] = t("Highest $value !points", userpoints_translation());;
} //foreach
return $blocks;
case 'view':
if (user_access(USERPOINTS_PERM_VIEW)) {
if ($delta == -1) {
$title = t('@user\'s !points', array_merge(array('@user' => $user->name), userpoints_translation()));;
if ($user->uid) {
$points = (int) db_result(db_query('SELECT points FROM {userpoints} WHERE uid = %d', $user->uid));
$show_points = format_plural($points, t('!point', userpoints_translation()), t('!points', userpoints_translation()));
$content = t('You have %p %c', array('%p' => $points, '%c' => $show_points));
}
else {
$content = t('!Points are visible to logged in users only', userpoints_translation());
}
}
else {
//$delta is our tid for pulling the points
//if 0 we pull 0 or NULL
$title = t('Highest Users');
$num = variable_get('userpoints_block_up_records_'. $delta, 5);
$sql = 'SELECT p.uid, u.name, p.points
FROM {userpoints} p
INNER JOIN {users} u USING (uid)';
if ( $delta == 0 ) {
$sql .= ' WHERE p.tid = 0 OR p.tid IS NULL ORDER BY p.points DESC';
$result = db_query_range($sql, 0, $num);
}
else {
$sql .= ' WHERE p.tid = %d ORDER BY p.points DESC';
$result = db_query_range($sql, $delta, 0, $num);
}
while ($data = db_fetch_object($result)) {
$rows[] =
array(
array('data' => theme('username', $data)),
array('data' => $data->points, 'align' => 'right'));
}
$header = array(t('User'), t('!Points', userpoints_translation()));
$content = theme('table', $header, $rows);
$content .= '
";
if ($args['subtotals']) {
foreach ($args['subtotals'] as $tid => $data) {
$output .= ''. $data['name'] .' '. t('!points Balance', userpoints_translation()) .': '. $data['total'] .'
';
}
}
$output .= "
";
$output .= ''. t('Approved !points Balance', userpoints_translation()) .': '. $args['approved_total'] .'
';
$output .= ''. t('!Points awaiting moderation', userpoints_translation()) .': '. $args['unapproved_total'] .'
';
$output .= ''. t('Net !points Balance', userpoints_translation()) .': '. $args['overall_total'] .'
';
$output .= "