SMF SSI.php Functions
Current Version 1.1
This file is used to demonstrate the capabilities of SSI.php using SHTML include functions.
The examples the include tag, then the results of it. Examples are separated by horizontal rules.
Recent Topics Function: <!--#include virtual="./SSI.php?ssi_function=recentTopics" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Recent Posts Function: <!--#include virtual="./SSI.php?ssi_function=recentPosts" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Recent Poll Function: <!--#include virtual="./SSI.php?ssi_function=recentPoll" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Top Boards Function: <!--#include virtual="./SSI.php?ssi_function=topBoards" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Top Topics by View Function: <!--#include virtual="./SSI.php?ssi_function=topTopicsViews" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Top Topics by Replies Function: <!--#include virtual="./SSI.php?ssi_function=topTopicsReplies" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Top Poll Function: <!--#include virtual="./SSI.php?ssi_function=topPoll" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Top Poster Function: <!--#include virtual="./SSI.php?ssi_function=topPoster" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Topic's Poll Function: <!--#include virtual="./SSI.php?ssi_function=showPoll;ssi_topic=##" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Latest Member Function: <!--#include virtual="./SSI.php?ssi_function=latestMember" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Board Stats: <!--#include virtual="./SSI.php?ssi_function=boardStats" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Who's Online Function: <!--#include virtual="./SSI.php?ssi_function=whosOnline" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Log Online Presence + Who's Online Function: <!--#include virtual="./SSI.php?ssi_function=logOnline" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Welcome Function: <!--#include virtual="./SSI.php?ssi_function=welcome" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
News Function: <!--#include virtual="./SSI.php?ssi_function=news" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Board News Function: <!--#include virtual="./SSI.php?ssi_function=boardNews" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Menubar Function: <!--#include virtual="./SSI.php?ssi_function=menubar" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Quick Search Function: <!--#include virtual="./SSI.php?ssi_function=quickSearch" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Login Function: <!--#include virtual="./SSI.php?ssi_function=login" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Log Out Function: <!--#include virtual="./SSI.php?ssi_function=logout" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Today's Birthdays Function: <!--#include virtual="./SSI.php?ssi_function=todaysBirthdays" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Today's Holidays Function: <!--#include virtual="./SSI.php?ssi_function=todaysHolidays" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Today's Events Function: <!--#include virtual="./SSI.php?ssi_function=todaysEvents" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Today's Calendar Function: <!--#include virtual="./SSI.php?ssi_function=todaysCalendar" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
Recent Calendar Events Function: <!--#include virtual="./SSI.php?ssi_function=recentEvents" -->
xt['users'];
// Hidden users, or buddies?
if ($return['hidden'] > 0 || $show_buddies)
echo '
(' . ($show_buddies ? ($return['buddies'] . ' ' . ($return['buddies'] == 1 ? $txt['buddy'] : $txt['buddies'])) : '') . ($show_buddies && $return['hidden'] ? ', ' : '') . (!$return['hidden'] ? '' : $return['hidden'] . ' ' . $txt['hidden']) . ')';
echo ' ';
foreach ($return['users'] as $user)
echo $user['hidden'] ? '' . $user['link'] . ' ' : $user['link'], $user['is_last'] ? '' : ', ';
}
// Just like whosOnline except it also logs the online presence.
function ssi_logOnline($output_method = 'echo')
{
writeLog();
if ($output_method != 'echo')
return ssi_whosOnline($output_method);
else
ssi_whosOnline($output_method);
}
// Shows a login box.
function ssi_login($redirect_to = '', $output_method = 'echo')
{
global $scripturl, $txt, $user_info, $context;
if ($redirect_to != '')
$_SESSION['login_url'] = $redirect_to;
if ($output_method != 'echo' || !$user_info['is_guest'])
return $user_info['is_guest'];
echo '
';
}
// Show the most-voted-in poll.
function ssi_topPoll($output_method = 'echo')
{
// Just use recentPoll, no need to duplicate code...
return ssi_recentPoll($output_method, true);
}
// Show the most recently posted poll.
function ssi_recentPoll($output_method = 'echo', $topPollInstead = false)
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = array_intersect(boardsAllowedTo('poll_view'), boardsAllowedTo('poll_vote'));
if (empty($boardsAllowed))
return array();
$request = db_query("
SELECT p.ID_POLL, p.question, t.ID_TOPIC, p.maxVotes
FROM ({$db_prefix}polls AS p, {$db_prefix}boards AS b, {$db_prefix}topics AS t" . ($topPollInstead ? ", {$db_prefix}poll_choices AS pc" : '') . ")
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.votingLocked = 0" . ($topPollInstead ? "
AND pc.ID_POLL = p.ID_POLL" : '') . "
AND lp.ID_CHOICE IS NULL
AND t.ID_POLL = p.ID_POLL
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
ORDER BY " . ($topPollInstead ? 'pc.votes' : 'p.ID_POLL') . " DESC
LIMIT 1", __FILE__, __LINE__);
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// This user has voted on all the polls.
if ($row === false)
return array();
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => 'poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => false,
'topic' => $row['ID_TOPIC'],
'options' => array()
);
// Calculate the percentages and bar lengths...
$divisor = $return['total_votes'] == 0 ? 1 : $return['total_votes'];
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
echo '
';
}
function ssi_showPoll($topic = null, $output_method = 'echo')
{
global $db_prefix, $txt, $ID_MEMBER, $settings, $boardurl, $sc, $user_info;
global $context;
$boardsAllowed = boardsAllowedTo('poll_view');
if (empty($boardsAllowed))
return array();
if ($topic === null && isset($_REQUEST['ssi_topic']))
$topic = (int) $_REQUEST['ssi_topic'];
else
$topic = (int) $topic;
$request = db_query("
SELECT
p.ID_POLL, p.question, p.votingLocked, p.hideResults, p.expireTime, p.maxVotes, b.ID_BOARD
FROM ({$db_prefix}topics AS t, {$db_prefix}polls AS p, {$db_prefix}boards AS b)
WHERE p.ID_POLL = t.ID_POLL
AND t.ID_TOPIC = $topic
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]" . (!in_array(0, $boardsAllowed) ? "
AND b.ID_BOARD IN (" . implode(', ', $boardsAllowed) . ")" : '') . "
LIMIT 1", __FILE__, __LINE__);
// Either this topic has no poll, or the user cannot view it.
if (mysql_num_rows($request) == 0)
return array();
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
// Check if they can vote.
if (!empty($row['expireTime']) && $row['expireTime'] < time())
$allow_vote = false;
elseif ($user_info['is_guest'] || !empty($row['votingLocked']) || !allowedTo('poll_vote', array($row['ID_BOARD'])))
$allow_vote = false;
else
{
$request = db_query("
SELECT ID_MEMBER
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]
AND ID_MEMBER = $ID_MEMBER
LIMIT 1", __FILE__, __LINE__);
$allow_vote = mysql_num_rows($request) == 0;
mysql_free_result($request);
}
$request = db_query("
SELECT COUNT(DISTINCT ID_MEMBER)
FROM {$db_prefix}log_polls
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
list ($total) = mysql_fetch_row($request);
mysql_free_result($request);
$request = db_query("
SELECT ID_CHOICE, label, votes
FROM {$db_prefix}poll_choices
WHERE ID_POLL = $row[ID_POLL]", __FILE__, __LINE__);
$options = array();
$total_votes = 0;
while ($rowChoice = mysql_fetch_assoc($request))
{
censorText($rowChoice['label']);
$options[$rowChoice['ID_CHOICE']] = array($rowChoice['label'], $rowChoice['votes']);
$total_votes += $rowChoice['votes'];
}
mysql_free_result($request);
$return = array(
'id' => $row['ID_POLL'],
'image' => empty($pollinfo['votingLocked']) ? 'poll' : 'locked_poll',
'question' => $row['question'],
'total_votes' => $total,
'is_locked' => !empty($pollinfo['votingLocked']),
'allow_vote' => $allow_vote,
'topic' => $topic
);
// Calculate the percentages and bar lengths...
$divisor = $total_votes == 0 ? 1 : $total_votes;
foreach ($options as $i => $option)
{
$bar = floor(($option[1] * 100) / $divisor);
$barWide = $bar == 0 ? 1 : floor(($bar * 5) / 3);
$return['options'][$i] = array(
'id' => 'options-' . $i,
'percent' => $bar,
'votes' => $option[1],
'bar' => ' ',
'option' => parse_bbc($option[0]),
'vote_button' => ' '
);
}
$return['allowed_warning'] = $row['maxVotes'] > 1 ? sprintf($txt['poll_options6'], $row['maxVotes']) : '';
if ($output_method != 'echo')
return $return;
if ($return['allow_vote'])
{
echo '
';
}
else
{
echo '
', $return['question'], '
';
foreach ($return['options'] as $option)
echo '
', $option['option'], '
', $option['bar'], ' ', $option['votes'], ' (', $option['percent'], '%)
';
echo '
', $txt['smf24'], ': ', $return['total_votes'], '
';
}
}
// Takes care of voting - don't worry, this is done automatically.
function ssi_pollVote()
{
global $db_prefix, $ID_MEMBER, $user_info, $sc;
if (!isset($_POST['sc']) || $_POST['sc'] != $sc || empty($_POST['options']) || !isset($_POST['poll']))
{
echo '
«
';
return;
}
// This can cause weird errors! (ie. copyright missing.)
checkSession();
$_POST['poll'] = (int) $_POST['poll'];
// Check if they have already voted, or voting is locked.
$request = db_query("
SELECT IFNULL(lp.ID_CHOICE, -1) AS selected, p.votingLocked, p.expireTime, p.maxVotes, t.ID_TOPIC
FROM ({$db_prefix}polls AS p, {$db_prefix}topics AS t, {$db_prefix}boards AS b)
LEFT JOIN {$db_prefix}log_polls AS lp ON (lp.ID_POLL = p.ID_POLL AND lp.ID_MEMBER = $ID_MEMBER)
WHERE p.ID_POLL = $_POST[poll]
AND t.ID_POLL = $_POST[poll]
AND b.ID_BOARD = t.ID_BOARD
AND $user_info[query_see_board]
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
die;
$row = mysql_fetch_assoc($request);
mysql_free_result($request);
if (!empty($row['votingLocked']) || $row['selected'] != -1 || (!empty($row['expireTime']) && time() > $row['expireTime']))
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
// Too many options checked?
if (count($_REQUEST['options']) > $row['maxVotes'])
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
$options = array();
$setString = '';
foreach ($_REQUEST['options'] as $id)
{
$id = (int) $id;
$options[] = $id;
$setString .= "
($_POST[poll], $ID_MEMBER, $id),";
}
$setString = substr($setString, 0, -1);
// Add their vote in to the tally.
db_query("
INSERT INTO {$db_prefix}log_polls
(ID_POLL, ID_MEMBER, ID_CHOICE)
VALUES $setString", __FILE__, __LINE__);
db_query("
UPDATE {$db_prefix}poll_choices
SET votes = votes + 1
WHERE ID_POLL = $_POST[poll]
AND ID_CHOICE IN (" . implode(', ', $options) . ")
LIMIT " . count($options), __FILE__, __LINE__);
redirectexit('topic=' . $row['ID_TOPIC'] . '.0');
}
// Show a search box.
function ssi_quickSearch($output_method = 'echo')
{
global $scripturl, $txt, $context;
if ($output_method != 'echo')
return $scripturl . '?action=search';
echo '
';
}
// Show what would be the forum news.
function ssi_news($output_method = 'echo')
{
global $context;
if ($output_method != 'echo')
return $context['random_news_line'];
echo $context['random_news_line'];
}
// Show today's birthdays.
function ssi_todaysBirthdays($output_method = 'echo')
{
global $context, $scripturl;
if (!smf_loadCalendarInfo() || empty($context['calendar_birthdays']))
return array();
if ($output_method != 'echo')
return $context['calendar_birthdays'];
foreach ($context['calendar_birthdays'] as $member)
echo '
' . $member['name'] . (isset($member['age']) ? ' (' . $member['age'] . ')' : '') . ' ' . (!$member['is_last'] ? ', ' : '');
}
// Show today's holidays.
function ssi_todaysHolidays($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_holidays']))
return array();
if ($output_method != 'echo')
return $context['calendar_holidays'];
echo '
', implode(', ', $context['calendar_holidays']);
}
// Show today's events.
function ssi_todaysEvents($output_method = 'echo')
{
global $context;
if (!smf_loadCalendarInfo() || empty($context['calendar_events']))
return array();
if ($output_method != 'echo')
return $context['calendar_events'];
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Show all calendar entires for today. (birthdays, holodays, and events.)
function ssi_todaysCalendar($output_method = 'echo')
{
global $context, $modSettings, $txt, $scripturl;
if (!smf_loadCalendarInfo())
return array();
if ($output_method != 'echo')
return array(
'birthdays' => $context['calendar_birthdays'],
'holidays' => $context['calendar_holidays'],
'events' => $context['calendar_events']
);
if (!empty($context['calendar_holidays']))
echo '
' . $txt['calendar5'] . ' ' . implode(', ', $context['calendar_holidays']) . ' ';
if (!empty($context['calendar_birthdays']))
{
echo '
' . $txt['calendar3b'] . ' ';
foreach ($context['calendar_birthdays'] as $member)
echo '
', $member['name'], isset($member['age']) ? ' (' . $member['age'] . ')' : '', ' ', !$member['is_last'] ? ', ' : '';
echo '
';
}
if (!empty($context['calendar_events']))
{
echo '
' . $txt['calendar4b'] . ' ';
foreach ($context['calendar_events'] as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
}
// Show the latest news, with a template... by board.
function ssi_boardNews($board = null, $limit = null, $start = null, $length = null, $output_method = 'echo')
{
global $scripturl, $db_prefix, $txt, $settings, $modSettings, $context;
global $func;
loadLanguage('Stats');
// Must be integers....
if ($limit === null)
$limit = isset($_GET['limit']) ? (int) $_GET['limit'] : 5;
else
$limit = (int) $limit;
if ($start === null)
$start = isset($_GET['start']) ? (int) $_GET['start'] : 0;
else
$start = (int) $start;
if ($board !== null)
$board = (int) $board;
elseif (isset($_GET['board']))
$board = (int) $_GET['board'];
if ($length === null)
$length = isset($_GET['length']) ? (int) $_GET['length'] : 0;
else
$length = (int) $length;
$limit = max(0, $limit);
$start = max(0, $start);
// Make sure guests can see this board.
$request = db_query("
SELECT ID_BOARD
FROM {$db_prefix}boards
WHERE " . ($board === null ? '' : "ID_BOARD = $board
AND ") . "FIND_IN_SET(-1, memberGroups)
LIMIT 1", __FILE__, __LINE__);
if (mysql_num_rows($request) == 0)
{
if ($output_method == 'echo')
die($txt['smf_news_error2']);
else
return array();
}
list ($board) = mysql_fetch_row($request);
mysql_free_result($request);
// Load the message icons - the usual suspects.
$stable_icons = array('xx', 'thumbup', 'thumbdown', 'exclamation', 'question', 'lamp', 'smiley', 'angry', 'cheesy', 'grin', 'sad', 'wink', 'moved', 'recycled', 'wireless');
$icon_sources = array();
foreach ($stable_icons as $icon)
$icon_sources[$icon] = 'images_url';
// Find the post ids.
$request = db_query("
SELECT ID_FIRST_MSG
FROM {$db_prefix}topics
WHERE ID_BOARD = $board
ORDER BY ID_FIRST_MSG DESC
LIMIT $start, $limit", __FILE__, __LINE__);
$posts = array();
while ($row = mysql_fetch_assoc($request))
$posts[] = $row['ID_FIRST_MSG'];
mysql_free_result($request);
if (empty($posts))
return array();
// Find the posts.
$request = db_query("
SELECT
m.icon, m.subject, m.body, IFNULL(mem.realName, m.posterName) AS posterName, m.posterTime,
t.numReplies, t.ID_TOPIC, m.ID_MEMBER, m.smileysEnabled, m.ID_MSG, t.locked
FROM ({$db_prefix}topics AS t, {$db_prefix}messages AS m)
LEFT JOIN {$db_prefix}members AS mem ON (mem.ID_MEMBER = m.ID_MEMBER)
WHERE t.ID_FIRST_MSG IN (" . implode(', ', $posts) . ")
AND m.ID_MSG = t.ID_FIRST_MSG
ORDER BY t.ID_FIRST_MSG DESC
LIMIT " . count($posts), __FILE__, __LINE__);
$return = array();
while ($row = mysql_fetch_assoc($request))
{
// If we want to limit the length of the post.
if (!empty($length) && $func['strlen']($row['body']) > $length)
{
$row['body'] = $func['substr']($row['body'], 0, $length);
// The first space or line break. ( , etc.)
$cutoff = max(strrpos($row['body'], ' '), strrpos($row['body'], '<'));
if ($cutoff !== false)
$row['body'] = $func['substr']($row['body'], 0, $cutoff);
$row['body'] .= '...';
}
$row['body'] = parse_bbc($row['body'], $row['smileysEnabled'], $row['ID_MSG']);
// Check that this message icon is there...
if (empty($modSettings['messageIconChecks_disable']) && !isset($icon_sources[$row['icon']]))
$icon_sources[$row['icon']] = file_exists($settings['theme_dir'] . '/images/post/' . $row['icon'] . '.gif') ? 'images_url' : 'default_images_url';
censorText($row['subject']);
censorText($row['body']);
$return[] = array(
'id' => $row['ID_TOPIC'],
'message_id' => $row['ID_MSG'],
'icon' => ' ',
'subject' => $row['subject'],
'time' => timeformat($row['posterTime']),
'timestamp' => forum_time(true, $row['posterTime']),
'body' => $row['body'],
'href' => $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => '' . $row['numReplies'] . ' ' . ($row['numReplies'] == 1 ? $txt['smf_news_1'] : $txt['smf_news_2']) . ' ',
'replies' => $row['numReplies'],
'comment_href' => !empty($row['locked']) ? '' : $scripturl . '?action=post;topic=' . $row['ID_TOPIC'] . '.' . $row['numReplies'] . ';num_replies=' . $row['numReplies'],
'comment_link' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'new_comment' => !empty($row['locked']) ? '' : '' . $txt['smf_news_3'] . ' ',
'poster' => array(
'id' => $row['ID_MEMBER'],
'name' => $row['posterName'],
'href' => !empty($row['ID_MEMBER']) ? $scripturl . '?action=profile;u=' . $row['ID_MEMBER'] : '',
'link' => !empty($row['ID_MEMBER']) ? '' . $row['posterName'] . ' ' : $row['posterName']
),
'locked' => !empty($row['locked']),
'is_last' => false
);
}
mysql_free_result($request);
if (empty($return))
return $return;
$return[count($return) - 1]['is_last'] = true;
if ($output_method != 'echo')
return $return;
foreach ($return as $news)
{
echo '
', $news['icon'], ' ', $news['subject'], '
', $news['time'], ' ', $txt[525], ' ', $news['poster']['link'], '
', $news['body'], '
', $news['link'], $news['locked'] ? '' : ' | ' . $news['comment_link'], '
';
if (!$news['is_last'])
echo '
';
}
}
// Show the most recent events.
function ssi_recentEvents($max_events = 7, $output_method = 'echo')
{
global $db_prefix, $user_info, $scripturl, $modSettings, $txt, $sc, $ID_MEMBER;
// Find all events which are happening in the near future that the member can see.
$request = db_query("
SELECT
cal.ID_EVENT, cal.startDate, cal.endDate, cal.title, cal.ID_MEMBER, cal.ID_TOPIC,
cal.ID_BOARD, t.ID_FIRST_MSG
FROM {$db_prefix}calendar AS cal
LEFT JOIN {$db_prefix}boards AS b ON (b.ID_BOARD = cal.ID_BOARD)
LEFT JOIN {$db_prefix}topics AS t ON (t.ID_TOPIC = cal.ID_TOPIC)
WHERE cal.startDate <= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND cal.endDate >= '" . strftime('%Y-%m-%d', forum_time(false)) . "'
AND (cal.ID_BOARD = 0 OR $user_info[query_see_board])
ORDER BY cal.startDate DESC
LIMIT $max_events", __FILE__, __LINE__);
$return = array();
$duplicates = array();
while ($row = mysql_fetch_assoc($request))
{
// Check if we've already come by an event linked to this same topic with the same title... and don't display it if we have.
if (!empty($duplicates[$row['title'] . $row['ID_TOPIC']]))
continue;
// Censor the title.
censorText($row['title']);
if ($row['startDate'] < strftime('%Y-%m-%d', forum_time(false)))
$date = strftime('%Y-%m-%d', forum_time(false));
else
$date = $row['startDate'];
$return[$date][] = array(
'id' => $row['ID_EVENT'],
'title' => $row['title'],
'can_edit' => allowedTo('calendar_edit_any') || ($row['ID_MEMBER'] == $ID_MEMBER && allowedTo('calendar_edit_own')),
'modify_href' => $scripturl . '?action=' . ($row['ID_BOARD'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $row['ID_FIRST_MSG'] . ';topic=' . $row['ID_TOPIC'] . '.0;calendar;') . 'eventid=' . $row['ID_EVENT'] . ';sesc=' . $sc,
'href' => $row['ID_BOARD'] == 0 ? '' : $scripturl . '?topic=' . $row['ID_TOPIC'] . '.0',
'link' => $row['ID_BOARD'] == 0 ? $row['title'] : '' . $row['title'] . ' ',
'start_date' => $row['startDate'],
'end_date' => $row['endDate'],
'is_last' => false
);
// Let's not show this one again, huh?
$duplicates[$row['title'] . $row['ID_TOPIC']] = true;
}
mysql_free_result($request);
foreach ($return as $mday => $array)
$return[$mday][count($array) - 1]['is_last'] = true;
if ($output_method != 'echo' || empty($return))
return $return;
// Well the output method is echo.
echo '
' . $txt['calendar4'] . ' ';
foreach ($return as $mday => $array)
foreach ($array as $event)
{
if ($event['can_edit'])
echo '
* ';
echo '
' . $event['link'] . (!$event['is_last'] ? ', ' : '');
}
}
// Load the calendar information. (internal...)
function smf_loadCalendarInfo()
{
global $modSettings, $context, $user_info, $scripturl, $sc, $ID_MEMBER;
// Get the current forum time and check whether the statistics are up to date.
if (!isset($modSettings['cal_today_updated']) || $modSettings['cal_today_updated'] != strftime('%Y%m%d', forum_time(false)))
updateStats('calendar');
// Load the holidays for today...
if (isset($modSettings['cal_today_holiday']))
$holidays = unserialize($modSettings['cal_today_holiday']);
// ... the birthdays for today...
if (isset($modSettings['cal_today_birthday']))
$bday = unserialize($modSettings['cal_today_birthday']);
// ... and the events for today.
if (isset($modSettings['cal_today_event']))
$events = unserialize($modSettings['cal_today_event']);
// No events, birthdays, or holidays... don't show anything.
if (empty($holidays) && empty($bday) && empty($events))
return false;
// This shouldn't be less than one!
if (empty($modSettings['cal_days_for_index']) || $modSettings['cal_days_for_index'] < 1)
$days_for_index = 86400;
else
$days_for_index = $modSettings['cal_days_for_index'] * 86400;
$context['calendar_only_today'] = $modSettings['cal_days_for_index'] == 1;
// Get the current member time/date.
$now = forum_time();
// This is used to show the "how-do-I-edit" help.
$context['calendar_can_edit'] = allowedTo('calendar_edit_any');
// Holidays between now and now + days.
$context['calendar_holidays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($holidays[strftime('%Y-%m-%d', $i)]))
$context['calendar_holidays'] = array_merge($context['calendar_holidays'], $holidays[strftime('%Y-%m-%d', $i)]);
}
// Happy Birthday, guys and gals!
$context['calendar_birthdays'] = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($bday[strftime('%Y-%m-%d', $i)]))
{
foreach ($bday[strftime('%Y-%m-%d', $i)] as $index => $dummy)
$bday[strftime('%Y-%m-%d', $i)][$index]['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$context['calendar_birthdays'] = array_merge($context['calendar_birthdays'], $bday[strftime('%Y-%m-%d', $i)]);
}
}
$context['calendar_events'] = array();
$duplicates = array();
for ($i = $now; $i < $now + $days_for_index; $i += 86400)
{
if (isset($events[strftime('%Y-%m-%d', $i)]))
foreach ($events[strftime('%Y-%m-%d', $i)] as $ev => $event)
{
if (empty($event['topic']) || (count(array_intersect($user_info['groups'], $event['allowed_groups'])) != 0 || allowedTo('admin_forum')))
{
if (isset($duplicates[$events[strftime('%Y-%m-%d', $i)][$ev]['topic'] . $events[strftime('%Y-%m-%d', $i)][$ev]['title']]))
{
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
continue;
}
$this_event = &$events[strftime('%Y-%m-%d', $i)][$ev];
$this_event['href'] = $this_event['topic'] == 0 ? '' : $scripturl . '?topic=' . $this_event['topic'] . '.0';
$this_event['link'] = $this_event['topic'] == 0 ? $this_event['title'] : '' . $this_event['title'] . ' ';
$this_event['modify_href'] = $scripturl . '?action=' . ($this_event['topic'] == 0 ? 'calendar;sa=post;' : 'post;msg=' . $this_event['msg'] . ';topic=' . $this_event['topic'] . '.0;calendar;') . 'eventid=' . $this_event['id'] . ';sesc=' . $sc;
$this_event['can_edit'] = allowedTo('calendar_edit_any') || ($this_event['poster'] == $ID_MEMBER && allowedTo('calendar_edit_own'));
$this_event['is_today'] = (strftime('%Y-%m-%d', $i)) == strftime('%Y-%m-%d', forum_time());
$this_event['date'] = strftime('%Y-%m-%d', $i);
$duplicates[$this_event['topic'] . $this_event['title']] = true;
}
else
unset($events[strftime('%Y-%m-%d', $i)][$ev]);
}
if (isset($events[strftime('%Y-%m-%d', $i)]))
$context['calendar_events'] = array_merge($context['calendar_events'], $events[strftime('%Y-%m-%d', $i)]);
}
for ($i = 0, $n = count($context['calendar_birthdays']); $i < $n; $i++)
$context['calendar_birthdays'][$i]['is_last'] = !isset($context['calendar_birthdays'][$i + 1]);
for ($i = 0, $n = count($context['calendar_events']); $i < $n; $i++)
$context['calendar_events'][$i]['is_last'] = !isset($context['calendar_events'][$i + 1]);
return !empty($context['calendar_holidays']) || !empty($context['calendar_birthdays']) || !empty($context['calendar_events']);
}
// Check the passed ID_MEMBER/password. If $is_username is true, treats $id as a username.
function ssi_checkPassword($id = null, $password = null, $is_username = false)
{
global $db_prefix, $sourcedir;
// If $id is null, this was most likely called from a query string and should do nothing.
if ($id === null)
return;
$request = db_query("
SELECT passwd, memberName, is_activated
FROM {$db_prefix}members
WHERE " . ($is_username ? 'memberName' : 'ID_MEMBER') . " = '$id'
LIMIT 1", __FILE__, __LINE__);
list ($pass, $user, $active) = mysql_fetch_row($request);
mysql_free_result($request);
return sha1(strtolower($user) . $password) == $pass && $active == 1;
}
?>
*ssi_examples.shtml last modified on 09/02/06