Add TINYIB_CAPTCHA
This commit is contained in:
parent
e7c69c9a95
commit
e2d433ff16
|
@ -70,6 +70,7 @@ if (isset($_POST['message']) || isset($_POST['file'])) {
|
||||||
list($loggedin, $isadmin) = manageCheckLogIn();
|
list($loggedin, $isadmin) = manageCheckLogIn();
|
||||||
$rawpost = isRawPost();
|
$rawpost = isRawPost();
|
||||||
if (!$loggedin) {
|
if (!$loggedin) {
|
||||||
|
checkCAPTCHA();
|
||||||
checkBanned();
|
checkBanned();
|
||||||
checkMessageSize();
|
checkMessageSize();
|
||||||
checkFlood();
|
checkFlood();
|
||||||
|
|
|
@ -0,0 +1,386 @@
|
||||||
|
<?php
|
||||||
|
/**
|
||||||
|
* Script for generation of CAPTCHAs
|
||||||
|
*
|
||||||
|
* @author Jose Rodriguez <jose.rodriguez@exec.cl>
|
||||||
|
* @license GPLv3
|
||||||
|
* @link http://code.google.com/p/cool-php-captcha
|
||||||
|
* @version 0.3
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
session_start();
|
||||||
|
putenv('GDFONTPATH=' . realpath('./fonts/'));
|
||||||
|
$captcha = new SimpleCaptcha();
|
||||||
|
$captcha->CreateImage();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* SimpleCaptcha class
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
class SimpleCaptcha {
|
||||||
|
/** Width of the image */
|
||||||
|
public $width = 175;
|
||||||
|
|
||||||
|
/** Height of the image */
|
||||||
|
public $height = 55;
|
||||||
|
|
||||||
|
/** Dictionary word file (empty for random text) */
|
||||||
|
public $wordsFile = '';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Path for resource files (fonts, words, etc.)
|
||||||
|
*
|
||||||
|
* "resources" by default. For security reasons, is better move this
|
||||||
|
* directory to another location outise the web server
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public $resourcesPath = './fonts';
|
||||||
|
|
||||||
|
/** Min word length (for non-dictionary random text generation) */
|
||||||
|
public $minWordLength = 4;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Max word length (for non-dictionary random text generation)
|
||||||
|
*
|
||||||
|
* Used for dictionary words indicating the word-length
|
||||||
|
* for font-size modification purposes
|
||||||
|
*/
|
||||||
|
public $maxWordLength = 6;
|
||||||
|
|
||||||
|
/** Sessionname to store the original text */
|
||||||
|
public $session_var = 'tinyibcaptcha';
|
||||||
|
|
||||||
|
/** Background color in RGB-array */
|
||||||
|
public $backgroundColor = array(254, 254, 254);
|
||||||
|
|
||||||
|
/** Foreground colors in RGB-array */
|
||||||
|
public $colors = array(
|
||||||
|
array(27, 78, 181), // blue
|
||||||
|
array(22, 163, 35), // green
|
||||||
|
array(214, 36, 7), // red
|
||||||
|
);
|
||||||
|
|
||||||
|
/** Shadow color in RGB-array or null */
|
||||||
|
public $shadowColor = array(0, 0, 0);
|
||||||
|
|
||||||
|
/** Horizontal line through the text */
|
||||||
|
public $lineWidth = 3;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Font configuration
|
||||||
|
*
|
||||||
|
* - font: TTF file
|
||||||
|
* - spacing: relative pixel space between character
|
||||||
|
* - minSize: min font size
|
||||||
|
* - maxSize: max font size
|
||||||
|
*/
|
||||||
|
public $fonts = array(
|
||||||
|
'Roboto-Regular' => array('spacing' => 0, 'minSize' => 27, 'maxSize' => 27, 'font' => 'roboto_regular.ttf'),
|
||||||
|
'Roboto-Bold' => array('spacing' => 0, 'minSize' => 27, 'maxSize' => 27, 'font' => 'roboto_bold.ttf')
|
||||||
|
);
|
||||||
|
|
||||||
|
/** Wave configuracion in X and Y axes */
|
||||||
|
public $Yperiod = 12;
|
||||||
|
public $Yamplitude = 14;
|
||||||
|
public $Xperiod = 11;
|
||||||
|
public $Xamplitude = 5;
|
||||||
|
|
||||||
|
/** letter rotation clockwise */
|
||||||
|
public $maxRotation = 8;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Internal image size factor (for better image quality)
|
||||||
|
* 1: low, 2: medium, 3: high
|
||||||
|
*/
|
||||||
|
public $scale = 3;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Blur effect for better image quality (but slower image processing).
|
||||||
|
* Better image results with scale=3
|
||||||
|
*/
|
||||||
|
public $blur = true;
|
||||||
|
|
||||||
|
/** Debug? */
|
||||||
|
public $debug = false;
|
||||||
|
|
||||||
|
/** Image format: jpeg or png */
|
||||||
|
public $imageFormat = 'png';
|
||||||
|
|
||||||
|
/** GD image */
|
||||||
|
public $im;
|
||||||
|
|
||||||
|
public function __construct($config = array()) {
|
||||||
|
}
|
||||||
|
|
||||||
|
public function CreateImage() {
|
||||||
|
$ini = microtime(true);
|
||||||
|
|
||||||
|
/** Initialization */
|
||||||
|
$this->ImageAllocate();
|
||||||
|
|
||||||
|
/** Text insertion */
|
||||||
|
$text = $this->GetCaptchaText();
|
||||||
|
$fontcfg = $this->fonts[array_rand($this->fonts)];
|
||||||
|
$this->WriteText($text, $fontcfg);
|
||||||
|
|
||||||
|
$_SESSION[$this->session_var] = $text;
|
||||||
|
|
||||||
|
/** Transformations */
|
||||||
|
if (!empty($this->lineWidth)) {
|
||||||
|
$this->WriteLine();
|
||||||
|
}
|
||||||
|
$this->WaveImage();
|
||||||
|
if ($this->blur && function_exists('imagefilter')) {
|
||||||
|
imagefilter($this->im, IMG_FILTER_GAUSSIAN_BLUR);
|
||||||
|
}
|
||||||
|
$this->ReduceImage();
|
||||||
|
|
||||||
|
if ($this->debug) {
|
||||||
|
imagestring($this->im, 1, 1, $this->height - 8,
|
||||||
|
"$text {$fontcfg['font']} " . round((microtime(true) - $ini) * 1000) . "ms",
|
||||||
|
$this->GdFgColor
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Output */
|
||||||
|
$this->WriteImage();
|
||||||
|
$this->Cleanup();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates the image resources
|
||||||
|
*/
|
||||||
|
protected function ImageAllocate() {
|
||||||
|
// Cleanup
|
||||||
|
if (!empty($this->im)) {
|
||||||
|
imagedestroy($this->im);
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->im = imagecreatetruecolor($this->width * $this->scale, $this->height * $this->scale);
|
||||||
|
|
||||||
|
// Background color
|
||||||
|
$this->GdBgColor = imagecolorallocate($this->im,
|
||||||
|
$this->backgroundColor[0],
|
||||||
|
$this->backgroundColor[1],
|
||||||
|
$this->backgroundColor[2]
|
||||||
|
);
|
||||||
|
imagefilledrectangle($this->im, 0, 0, $this->width * $this->scale, $this->height * $this->scale, $this->GdBgColor);
|
||||||
|
|
||||||
|
// Foreground color
|
||||||
|
$color = $this->colors[mt_rand(0, sizeof($this->colors) - 1)];
|
||||||
|
$this->GdFgColor = imagecolorallocate($this->im, $color[0], $color[1], $color[2]);
|
||||||
|
|
||||||
|
// Shadow color
|
||||||
|
if (!empty($this->shadowColor) && is_array($this->shadowColor) && sizeof($this->shadowColor) >= 3) {
|
||||||
|
$this->GdShadowColor = imagecolorallocate($this->im,
|
||||||
|
$this->shadowColor[0],
|
||||||
|
$this->shadowColor[1],
|
||||||
|
$this->shadowColor[2]
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Text generation
|
||||||
|
*
|
||||||
|
* @return string Text
|
||||||
|
*/
|
||||||
|
protected function GetCaptchaText() {
|
||||||
|
$text = $this->GetDictionaryCaptchaText();
|
||||||
|
if (!$text) {
|
||||||
|
$text = $this->GetRandomCaptchaText();
|
||||||
|
}
|
||||||
|
return $text;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Random text generation
|
||||||
|
*
|
||||||
|
* @return string Text
|
||||||
|
*/
|
||||||
|
protected function GetRandomCaptchaText($length = null) {
|
||||||
|
if (empty($length)) {
|
||||||
|
$length = rand($this->minWordLength, $this->maxWordLength);
|
||||||
|
}
|
||||||
|
|
||||||
|
$words = "abcdefghijlmnopqrstvwyz";
|
||||||
|
$vocals = "aeiou";
|
||||||
|
|
||||||
|
$text = "";
|
||||||
|
$vocal = rand(0, 1);
|
||||||
|
for ($i = 0; $i < $length; $i++) {
|
||||||
|
if ($vocal) {
|
||||||
|
$text .= substr($vocals, mt_rand(0, 4), 1);
|
||||||
|
} else {
|
||||||
|
$text .= substr($words, mt_rand(0, 22), 1);
|
||||||
|
}
|
||||||
|
$vocal = !$vocal;
|
||||||
|
}
|
||||||
|
return $text;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Random dictionary word generation
|
||||||
|
*
|
||||||
|
* @param boolean $extended Add extended "fake" words
|
||||||
|
* @return string Word
|
||||||
|
*/
|
||||||
|
function GetDictionaryCaptchaText($extended = false) {
|
||||||
|
if (empty($this->wordsFile)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Full path of words file
|
||||||
|
if (substr($this->wordsFile, 0, 1) == '/') {
|
||||||
|
$wordsfile = $this->wordsFile;
|
||||||
|
} else {
|
||||||
|
$wordsfile = $this->resourcesPath . '/' . $this->wordsFile;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!file_exists($wordsfile)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
$fp = fopen($wordsfile, "r");
|
||||||
|
$length = strlen(fgets($fp));
|
||||||
|
if (!$length) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
$line = rand(1, (filesize($wordsfile) / $length) - 2);
|
||||||
|
if (fseek($fp, $length * $line) == -1) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
$text = trim(fgets($fp));
|
||||||
|
fclose($fp);
|
||||||
|
|
||||||
|
/** Change ramdom volcals */
|
||||||
|
if ($extended) {
|
||||||
|
$text = preg_split('//', $text, -1, PREG_SPLIT_NO_EMPTY);
|
||||||
|
$vocals = array('a', 'e', 'i', 'o', 'u');
|
||||||
|
foreach ($text as $i => $char) {
|
||||||
|
if (mt_rand(0, 1) && in_array($char, $vocals)) {
|
||||||
|
$text[$i] = $vocals[mt_rand(0, 4)];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
$text = implode('', $text);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $text;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Horizontal line insertion
|
||||||
|
*/
|
||||||
|
protected function WriteLine() {
|
||||||
|
$x1 = $this->width * $this->scale * .15;
|
||||||
|
$x2 = $this->textFinalX;
|
||||||
|
$y1 = rand($this->height * $this->scale * .40, $this->height * $this->scale * .65);
|
||||||
|
$y2 = rand($this->height * $this->scale * .40, $this->height * $this->scale * .65);
|
||||||
|
$width = $this->lineWidth / 2 * $this->scale;
|
||||||
|
|
||||||
|
for ($i = $width * -1; $i <= $width; $i++) {
|
||||||
|
imageline($this->im, $x1, $y1 + $i, $x2, $y2 + $i, $this->GdFgColor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Text insertion
|
||||||
|
*/
|
||||||
|
protected function WriteText($text, $fontcfg = array()) {
|
||||||
|
if (empty($fontcfg)) {
|
||||||
|
// Select the font configuration
|
||||||
|
$fontcfg = $this->fonts[array_rand($this->fonts)];
|
||||||
|
}
|
||||||
|
|
||||||
|
$fontfile = $fontcfg['font'];
|
||||||
|
|
||||||
|
/** Increase font-size for shortest words: 9% for each glyph missing */
|
||||||
|
$lettersMissing = $this->maxWordLength - strlen($text);
|
||||||
|
$fontSizefactor = 1 + ($lettersMissing * 0.09);
|
||||||
|
|
||||||
|
// Text generation (char by char)
|
||||||
|
$x = 20 * $this->scale;
|
||||||
|
$y = round(($this->height * 27 / 40) * $this->scale);
|
||||||
|
$length = strlen($text);
|
||||||
|
for ($i = 0; $i < $length; $i++) {
|
||||||
|
$degree = rand($this->maxRotation * -1, $this->maxRotation);
|
||||||
|
$fontsize = rand($fontcfg['minSize'], $fontcfg['maxSize']) * $this->scale * $fontSizefactor;
|
||||||
|
$letter = substr($text, $i, 1);
|
||||||
|
|
||||||
|
if ($this->shadowColor) {
|
||||||
|
$coords = imagettftext($this->im, $fontsize, $degree,
|
||||||
|
$x + $this->scale, $y + $this->scale,
|
||||||
|
$this->GdShadowColor, $fontfile, $letter);
|
||||||
|
}
|
||||||
|
$coords = imagettftext($this->im, $fontsize, $degree,
|
||||||
|
$x, $y,
|
||||||
|
$this->GdFgColor, $fontfile, $letter);
|
||||||
|
$x += ($coords[2] - $x) + ($fontcfg['spacing'] * $this->scale);
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->textFinalX = $x;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Wave filter
|
||||||
|
*/
|
||||||
|
protected function WaveImage() {
|
||||||
|
// X-axis wave generation
|
||||||
|
$xp = $this->scale * $this->Xperiod * rand(1, 3);
|
||||||
|
$k = rand(0, 100);
|
||||||
|
for ($i = 0; $i < ($this->width * $this->scale); $i++) {
|
||||||
|
imagecopy($this->im, $this->im,
|
||||||
|
$i - 1, sin($k + $i / $xp) * ($this->scale * $this->Xamplitude),
|
||||||
|
$i, 0, 1, $this->height * $this->scale);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Y-axis wave generation
|
||||||
|
$k = rand(0, 100);
|
||||||
|
$yp = $this->scale * $this->Yperiod * rand(1, 2);
|
||||||
|
for ($i = 0; $i < ($this->height * $this->scale); $i++) {
|
||||||
|
imagecopy($this->im, $this->im,
|
||||||
|
sin($k + $i / $yp) * ($this->scale * $this->Yamplitude), $i - 1,
|
||||||
|
0, $i, $this->width * $this->scale, 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Reduce the image to the final size
|
||||||
|
*/
|
||||||
|
protected function ReduceImage() {
|
||||||
|
// Reduzco el tama<6D>o de la imagen
|
||||||
|
$imResampled = imagecreatetruecolor($this->width, $this->height);
|
||||||
|
imagecopyresampled($imResampled, $this->im,
|
||||||
|
0, 0, 0, 0,
|
||||||
|
$this->width, $this->height,
|
||||||
|
$this->width * $this->scale, $this->height * $this->scale
|
||||||
|
);
|
||||||
|
imagedestroy($this->im);
|
||||||
|
$this->im = $imResampled;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* File generation
|
||||||
|
*/
|
||||||
|
protected function WriteImage() {
|
||||||
|
if ($this->imageFormat == 'png' && function_exists('imagepng')) {
|
||||||
|
imagealphablending($this->im, true);
|
||||||
|
imagesavealpha($this->im, false);
|
||||||
|
imagecolortransparent($this->im, $this->GdBgColor);
|
||||||
|
|
||||||
|
header("Content-type: image/png");
|
||||||
|
imagepng($this->im);
|
||||||
|
} else {
|
||||||
|
header("Content-type: image/jpeg");
|
||||||
|
imagejpeg($this->im, null, 80);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Cleanup
|
||||||
|
*/
|
||||||
|
protected function Cleanup() {
|
||||||
|
imagedestroy($this->im);
|
||||||
|
}
|
||||||
|
}
|
|
@ -30,6 +30,9 @@ if (!defined('TINYIB_WEBM')) {
|
||||||
if (!defined('TINYIB_NOFILEOK')) {
|
if (!defined('TINYIB_NOFILEOK')) {
|
||||||
define('TINYIB_NOFILEOK', false);
|
define('TINYIB_NOFILEOK', false);
|
||||||
}
|
}
|
||||||
|
if (!defined('TINYIB_CAPTCHA')) {
|
||||||
|
define('TINYIB_CAPTCHA', false);
|
||||||
|
}
|
||||||
if (!defined('TINYIB_REQMOD')) {
|
if (!defined('TINYIB_REQMOD')) {
|
||||||
define('TINYIB_REQMOD', 'disable');
|
define('TINYIB_REQMOD', 'disable');
|
||||||
}
|
}
|
||||||
|
|
|
@ -71,9 +71,9 @@ class TableUtils {
|
||||||
/** Uses 'define' to create global constants for all the column names */
|
/** Uses 'define' to create global constants for all the column names */
|
||||||
function createDefines(&$tables) {
|
function createDefines(&$tables) {
|
||||||
foreach ($tables as $tablename => $discard) {
|
foreach ($tables as $tablename => $discard) {
|
||||||
$tabledef = & $tables[$tablename]; // PHP4 compatible
|
$tabledef = &$tables[$tablename]; // PHP4 compatible
|
||||||
foreach ($tabledef as $colname => $discard) {
|
foreach ($tabledef as $colname => $discard) {
|
||||||
$coldef = & $tabledef[$colname];
|
$coldef = &$tabledef[$colname];
|
||||||
define(strtoupper($tablename) . '_' . $colname, $coldef->index);
|
define(strtoupper($tablename) . '_' . $colname, $coldef->index);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,203 @@
|
||||||
|
Font data copyright Google 2012
|
||||||
|
|
||||||
|
Apache License
|
||||||
|
Version 2.0, January 2004
|
||||||
|
http://www.apache.org/licenses/
|
||||||
|
|
||||||
|
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||||
|
|
||||||
|
1. Definitions.
|
||||||
|
|
||||||
|
"License" shall mean the terms and conditions for use, reproduction,
|
||||||
|
and distribution as defined by Sections 1 through 9 of this document.
|
||||||
|
|
||||||
|
"Licensor" shall mean the copyright owner or entity authorized by
|
||||||
|
the copyright owner that is granting the License.
|
||||||
|
|
||||||
|
"Legal Entity" shall mean the union of the acting entity and all
|
||||||
|
other entities that control, are controlled by, or are under common
|
||||||
|
control with that entity. For the purposes of this definition,
|
||||||
|
"control" means (i) the power, direct or indirect, to cause the
|
||||||
|
direction or management of such entity, whether by contract or
|
||||||
|
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||||
|
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||||
|
|
||||||
|
"You" (or "Your") shall mean an individual or Legal Entity
|
||||||
|
exercising permissions granted by this License.
|
||||||
|
|
||||||
|
"Source" form shall mean the preferred form for making modifications,
|
||||||
|
including but not limited to software source code, documentation
|
||||||
|
source, and configuration files.
|
||||||
|
|
||||||
|
"Object" form shall mean any form resulting from mechanical
|
||||||
|
transformation or translation of a Source form, including but
|
||||||
|
not limited to compiled object code, generated documentation,
|
||||||
|
and conversions to other media types.
|
||||||
|
|
||||||
|
"Work" shall mean the work of authorship, whether in Source or
|
||||||
|
Object form, made available under the License, as indicated by a
|
||||||
|
copyright notice that is included in or attached to the work
|
||||||
|
(an example is provided in the Appendix below).
|
||||||
|
|
||||||
|
"Derivative Works" shall mean any work, whether in Source or Object
|
||||||
|
form, that is based on (or derived from) the Work and for which the
|
||||||
|
editorial revisions, annotations, elaborations, or other modifications
|
||||||
|
represent, as a whole, an original work of authorship. For the purposes
|
||||||
|
of this License, Derivative Works shall not include works that remain
|
||||||
|
separable from, or merely link (or bind by name) to the interfaces of,
|
||||||
|
the Work and Derivative Works thereof.
|
||||||
|
|
||||||
|
"Contribution" shall mean any work of authorship, including
|
||||||
|
the original version of the Work and any modifications or additions
|
||||||
|
to that Work or Derivative Works thereof, that is intentionally
|
||||||
|
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||||
|
or by an individual or Legal Entity authorized to submit on behalf of
|
||||||
|
the copyright owner. For the purposes of this definition, "submitted"
|
||||||
|
means any form of electronic, verbal, or written communication sent
|
||||||
|
to the Licensor or its representatives, including but not limited to
|
||||||
|
communication on electronic mailing lists, source code control systems,
|
||||||
|
and issue tracking systems that are managed by, or on behalf of, the
|
||||||
|
Licensor for the purpose of discussing and improving the Work, but
|
||||||
|
excluding communication that is conspicuously marked or otherwise
|
||||||
|
designated in writing by the copyright owner as "Not a Contribution."
|
||||||
|
|
||||||
|
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||||
|
on behalf of whom a Contribution has been received by Licensor and
|
||||||
|
subsequently incorporated within the Work.
|
||||||
|
|
||||||
|
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||||
|
this License, each Contributor hereby grants to You a perpetual,
|
||||||
|
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||||
|
copyright license to reproduce, prepare Derivative Works of,
|
||||||
|
publicly display, publicly perform, sublicense, and distribute the
|
||||||
|
Work and such Derivative Works in Source or Object form.
|
||||||
|
|
||||||
|
3. Grant of Patent License. Subject to the terms and conditions of
|
||||||
|
this License, each Contributor hereby grants to You a perpetual,
|
||||||
|
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||||
|
(except as stated in this section) patent license to make, have made,
|
||||||
|
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||||
|
where such license applies only to those patent claims licensable
|
||||||
|
by such Contributor that are necessarily infringed by their
|
||||||
|
Contribution(s) alone or by combination of their Contribution(s)
|
||||||
|
with the Work to which such Contribution(s) was submitted. If You
|
||||||
|
institute patent litigation against any entity (including a
|
||||||
|
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||||
|
or a Contribution incorporated within the Work constitutes direct
|
||||||
|
or contributory patent infringement, then any patent licenses
|
||||||
|
granted to You under this License for that Work shall terminate
|
||||||
|
as of the date such litigation is filed.
|
||||||
|
|
||||||
|
4. Redistribution. You may reproduce and distribute copies of the
|
||||||
|
Work or Derivative Works thereof in any medium, with or without
|
||||||
|
modifications, and in Source or Object form, provided that You
|
||||||
|
meet the following conditions:
|
||||||
|
|
||||||
|
(a) You must give any other recipients of the Work or
|
||||||
|
Derivative Works a copy of this License; and
|
||||||
|
|
||||||
|
(b) You must cause any modified files to carry prominent notices
|
||||||
|
stating that You changed the files; and
|
||||||
|
|
||||||
|
(c) You must retain, in the Source form of any Derivative Works
|
||||||
|
that You distribute, all copyright, patent, trademark, and
|
||||||
|
attribution notices from the Source form of the Work,
|
||||||
|
excluding those notices that do not pertain to any part of
|
||||||
|
the Derivative Works; and
|
||||||
|
|
||||||
|
(d) If the Work includes a "NOTICE" text file as part of its
|
||||||
|
distribution, then any Derivative Works that You distribute must
|
||||||
|
include a readable copy of the attribution notices contained
|
||||||
|
within such NOTICE file, excluding those notices that do not
|
||||||
|
pertain to any part of the Derivative Works, in at least one
|
||||||
|
of the following places: within a NOTICE text file distributed
|
||||||
|
as part of the Derivative Works; within the Source form or
|
||||||
|
documentation, if provided along with the Derivative Works; or,
|
||||||
|
within a display generated by the Derivative Works, if and
|
||||||
|
wherever such third-party notices normally appear. The contents
|
||||||
|
of the NOTICE file are for informational purposes only and
|
||||||
|
do not modify the License. You may add Your own attribution
|
||||||
|
notices within Derivative Works that You distribute, alongside
|
||||||
|
or as an addendum to the NOTICE text from the Work, provided
|
||||||
|
that such additional attribution notices cannot be construed
|
||||||
|
as modifying the License.
|
||||||
|
|
||||||
|
You may add Your own copyright statement to Your modifications and
|
||||||
|
may provide additional or different license terms and conditions
|
||||||
|
for use, reproduction, or distribution of Your modifications, or
|
||||||
|
for any such Derivative Works as a whole, provided Your use,
|
||||||
|
reproduction, and distribution of the Work otherwise complies with
|
||||||
|
the conditions stated in this License.
|
||||||
|
|
||||||
|
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||||
|
any Contribution intentionally submitted for inclusion in the Work
|
||||||
|
by You to the Licensor shall be under the terms and conditions of
|
||||||
|
this License, without any additional terms or conditions.
|
||||||
|
Notwithstanding the above, nothing herein shall supersede or modify
|
||||||
|
the terms of any separate license agreement you may have executed
|
||||||
|
with Licensor regarding such Contributions.
|
||||||
|
|
||||||
|
6. Trademarks. This License does not grant permission to use the trade
|
||||||
|
names, trademarks, service marks, or product names of the Licensor,
|
||||||
|
except as required for reasonable and customary use in describing the
|
||||||
|
origin of the Work and reproducing the content of the NOTICE file.
|
||||||
|
|
||||||
|
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||||
|
agreed to in writing, Licensor provides the Work (and each
|
||||||
|
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||||
|
implied, including, without limitation, any warranties or conditions
|
||||||
|
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||||
|
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||||
|
appropriateness of using or redistributing the Work and assume any
|
||||||
|
risks associated with Your exercise of permissions under this License.
|
||||||
|
|
||||||
|
8. Limitation of Liability. In no event and under no legal theory,
|
||||||
|
whether in tort (including negligence), contract, or otherwise,
|
||||||
|
unless required by applicable law (such as deliberate and grossly
|
||||||
|
negligent acts) or agreed to in writing, shall any Contributor be
|
||||||
|
liable to You for damages, including any direct, indirect, special,
|
||||||
|
incidental, or consequential damages of any character arising as a
|
||||||
|
result of this License or out of the use or inability to use the
|
||||||
|
Work (including but not limited to damages for loss of goodwill,
|
||||||
|
work stoppage, computer failure or malfunction, or any and all
|
||||||
|
other commercial damages or losses), even if such Contributor
|
||||||
|
has been advised of the possibility of such damages.
|
||||||
|
|
||||||
|
9. Accepting Warranty or Additional Liability. While redistributing
|
||||||
|
the Work or Derivative Works thereof, You may choose to offer,
|
||||||
|
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||||
|
or other liability obligations and/or rights consistent with this
|
||||||
|
License. However, in accepting such obligations, You may act only
|
||||||
|
on Your own behalf and on Your sole responsibility, not on behalf
|
||||||
|
of any other Contributor, and only if You agree to indemnify,
|
||||||
|
defend, and hold each Contributor harmless for any liability
|
||||||
|
incurred by, or claims asserted against, such Contributor by reason
|
||||||
|
of your accepting any such warranty or additional liability.
|
||||||
|
|
||||||
|
END OF TERMS AND CONDITIONS
|
||||||
|
|
||||||
|
APPENDIX: How to apply the Apache License to your work.
|
||||||
|
|
||||||
|
To apply the Apache License to your work, attach the following
|
||||||
|
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||||
|
replaced with your own identifying information. (Don't include
|
||||||
|
the brackets!) The text should be enclosed in the appropriate
|
||||||
|
comment syntax for the file format. We also recommend that a
|
||||||
|
file or class name and description of purpose be included on the
|
||||||
|
same "printed page" as the copyright notice for easier
|
||||||
|
identification within third-party archives.
|
||||||
|
|
||||||
|
Copyright [yyyy] [name of copyright owner]
|
||||||
|
|
||||||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
you may not use this file except in compliance with the License.
|
||||||
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
Unless required by applicable law or agreed to in writing, software
|
||||||
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
See the License for the specific language governing permissions and
|
||||||
|
limitations under the License.
|
Binary file not shown.
Binary file not shown.
|
@ -187,8 +187,8 @@ function writePage($filename, $contents) {
|
||||||
}
|
}
|
||||||
|
|
||||||
function fixLinksInRes($html) {
|
function fixLinksInRes($html) {
|
||||||
$search = array(' href="css/', ' src="js/', ' href="src/', ' href="thumb/', ' href="res/', ' href="imgboard.php', ' href="favicon.ico', 'src="thumb/', ' action="imgboard.php');
|
$search = array(' href="css/', ' src="js/', ' href="src/', ' href="thumb/', ' href="res/', ' href="imgboard.php', ' href="favicon.ico', 'src="thumb/', 'src="inc/', ' action="imgboard.php');
|
||||||
$replace = array(' href="../css/', ' src="../js/', ' href="../src/', ' href="../thumb/', ' href="../res/', ' href="../imgboard.php', ' href="../favicon.ico', 'src="../thumb/', ' action="../imgboard.php');
|
$replace = array(' href="../css/', ' src="../js/', ' href="../src/', ' href="../thumb/', ' href="../res/', ' href="../imgboard.php', ' href="../favicon.ico', 'src="../thumb/', 'src="../inc/', ' action="../imgboard.php');
|
||||||
|
|
||||||
return str_replace($search, $replace, $html);
|
return str_replace($search, $replace, $html);
|
||||||
}
|
}
|
||||||
|
@ -221,6 +221,21 @@ function deletePostImages($post) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function checkCAPTCHA() {
|
||||||
|
if (!TINYIB_CAPTCHA) {
|
||||||
|
return; // CAPTCHA is disabled
|
||||||
|
}
|
||||||
|
|
||||||
|
$captcha = isset($_POST['captcha']) ? strtolower(trim($_POST['captcha'])) : '';
|
||||||
|
$captcha_solution = isset($_SESSION['tinyibcaptcha']) ? strtolower(trim($_SESSION['tinyibcaptcha'])) : '';
|
||||||
|
|
||||||
|
if ($captcha == '') {
|
||||||
|
fancyDie('Please enter the CAPTCHA text.');
|
||||||
|
} else if ($captcha != $captcha_solution) {
|
||||||
|
fancyDie('Incorrect CAPTCHA text entered. Please try again.<br>Click the image to retrieve a new CAPTCHA.');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
function checkBanned() {
|
function checkBanned() {
|
||||||
$ban = banByIP($_SERVER['REMOTE_ADDR']);
|
$ban = banByIP($_SERVER['REMOTE_ADDR']);
|
||||||
if ($ban) {
|
if ($ban) {
|
||||||
|
|
22
inc/html.php
22
inc/html.php
|
@ -214,8 +214,19 @@ EOF;
|
||||||
$file_input_html = '';
|
$file_input_html = '';
|
||||||
$unique_posts_html = '';
|
$unique_posts_html = '';
|
||||||
|
|
||||||
if (TINYIB_REQMOD != 'disable') {
|
$captcha_html = '';
|
||||||
$reqmod_html = '<li>All posts' . (TINYIB_REQMOD == 'files' ? ' with a file attached' : '') . ' will be moderated before being shown.</li>';
|
if (TINYIB_CAPTCHA) {
|
||||||
|
$captcha_html = <<<EOF
|
||||||
|
<tr>
|
||||||
|
<td class="postblock">
|
||||||
|
CAPTCHA
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<input type="text" name="captcha" id="captcha" autocomplete="off" size="6" accesskey="c"> (enter the text below)<br>
|
||||||
|
<img id="captchaimage" src="inc/captcha.php" width="175" height="55" alt="CAPTCHA" onclick="javascript:reloadCAPTCHA()" style="margin-top: 5px;cursor: pointer;">
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
EOF;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (TINYIB_PIC || TINYIB_WEBM || TINYIB_SWF) {
|
if (TINYIB_PIC || TINYIB_WEBM || TINYIB_SWF) {
|
||||||
|
@ -238,6 +249,10 @@ EOF;
|
||||||
EOF;
|
EOF;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (TINYIB_REQMOD != 'disable') {
|
||||||
|
$reqmod_html = '<li>All posts' . (TINYIB_REQMOD == 'files' ? ' with a file attached' : '') . ' will be moderated before being shown.</li>';
|
||||||
|
}
|
||||||
|
|
||||||
$thumbnails_html = '';
|
$thumbnails_html = '';
|
||||||
if (TINYIB_PIC) {
|
if (TINYIB_PIC) {
|
||||||
$thumbnails_html = "<li>Images greater than $maxdimensions will be thumbnailed.</li>";
|
$thumbnails_html = "<li>Images greater than $maxdimensions will be thumbnailed.</li>";
|
||||||
|
@ -298,13 +313,14 @@ EOF;
|
||||||
<textarea id="message" name="message" cols="48" rows="4" accesskey="m"></textarea>
|
<textarea id="message" name="message" cols="48" rows="4" accesskey="m"></textarea>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
|
$captcha_html
|
||||||
$file_input_html
|
$file_input_html
|
||||||
<tr>
|
<tr>
|
||||||
<td class="postblock">
|
<td class="postblock">
|
||||||
Password
|
Password
|
||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
<input type="password" name="password" id="newpostpassword" size="8" accesskey="p"> (for post and file deletion)
|
<input type="password" name="password" id="newpostpassword" size="8" accesskey="p"> (for post and file deletion)
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
|
|
15
js/tinyib.js
15
js/tinyib.js
|
@ -23,6 +23,21 @@ function quotePost(postID) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function reloadCAPTCHA() {
|
||||||
|
var captcha_element = document.getElementById("captcha");
|
||||||
|
if (captcha_element) {
|
||||||
|
captcha_element.focus();
|
||||||
|
captcha_element.value = "";
|
||||||
|
}
|
||||||
|
|
||||||
|
var captchaimg_element = document.getElementById("captchaimage");
|
||||||
|
if (captchaimg_element) {
|
||||||
|
captchaimg_element.src += "#new";
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
document.addEventListener('DOMContentLoaded', function () {
|
document.addEventListener('DOMContentLoaded', function () {
|
||||||
var newpostpassword = document.getElementById("newpostpassword");
|
var newpostpassword = document.getElementById("newpostpassword");
|
||||||
if (newpostpassword) {
|
if (newpostpassword) {
|
||||||
|
|
|
@ -14,6 +14,7 @@ define('TINYIB_MODPASS', ""); // Moderators only have access to delete (
|
||||||
// Board description and behavior
|
// Board description and behavior
|
||||||
define('TINYIB_BOARD', "b"); // Unique identifier for this board using only letters and numbers
|
define('TINYIB_BOARD', "b"); // Unique identifier for this board using only letters and numbers
|
||||||
define('TINYIB_BOARDDESC', "TinyIB"); // Displayed at the top of every page
|
define('TINYIB_BOARDDESC', "TinyIB"); // Displayed at the top of every page
|
||||||
|
define('TINYIB_CAPTCHA', false); // Reduce spam by requiring users to pass a CAPTCHA when posting (click Rebuild All in the management panel after enabling)
|
||||||
define('TINYIB_REQMOD', "disable"); // Require moderation before displaying posts: disable / files / all (see README for instructions, only MySQL is supported)
|
define('TINYIB_REQMOD', "disable"); // Require moderation before displaying posts: disable / files / all (see README for instructions, only MySQL is supported)
|
||||||
|
|
||||||
// Board appearance
|
// Board appearance
|
||||||
|
|
Loading…
Reference in New Issue