2016-04-18 07:04:52 +00:00
|
|
|
<?php
|
|
|
|
|
2018-12-30 00:50:39 +00:00
|
|
|
function mkshield($left_str, $right_str, $color_str, $params=[]) {
|
2016-04-18 07:12:11 +00:00
|
|
|
$filename = sprintf(
|
|
|
|
"%s-%s-%s.svg",
|
|
|
|
rawurlencode(str_replace('-', '--', $left_str)),
|
|
|
|
rawurlencode(str_replace('-', '--', $right_str)),
|
|
|
|
rawurlencode($color_str)
|
|
|
|
);
|
2018-12-30 00:50:39 +00:00
|
|
|
if (count($params) > 0) {
|
|
|
|
$filename .= '?' . http_build_query($params);
|
|
|
|
}
|
2016-04-18 07:12:11 +00:00
|
|
|
|
2018-12-30 00:50:39 +00:00
|
|
|
$cache_path = SHIELDS_CACHE_DIR.urlencode($filename);
|
2016-04-18 07:04:52 +00:00
|
|
|
|
|
|
|
if (file_exists($cache_path)) {
|
|
|
|
return file_get_contents($cache_path);
|
|
|
|
|
|
|
|
} else {
|
|
|
|
$retn = file_get_contents('https://img.shields.io/badge/'.$filename);
|
2017-07-07 23:50:21 +00:00
|
|
|
|
|
|
|
// We need unique IDs
|
|
|
|
$prefix = substr(sha1($filename), 8).'-';
|
|
|
|
$retn = str_replace('id="', 'id="'.$prefix, $retn);
|
|
|
|
$retn = str_replace('url(#', 'url(#'.$prefix, $retn);
|
|
|
|
|
2016-04-18 07:04:52 +00:00
|
|
|
file_put_contents($cache_path, $retn);
|
|
|
|
return $retn;
|
|
|
|
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Create a thumbnail of an image. It overscales, centers, and crops to fit the
|
|
|
|
* target dimensions.
|
|
|
|
*
|
|
|
|
* @param string $src_file
|
|
|
|
* @param string $dest_file Null to return an image handle
|
|
|
|
* @param int $width
|
|
|
|
* @param int $height
|
|
|
|
* @return boolean
|
|
|
|
*/
|
|
|
|
function mkthumbnail($src_file, $dest_file, $width, $height) {
|
|
|
|
list($src_width, $src_height) = getimagesize($src_file);
|
|
|
|
|
|
|
|
$im = imagecreatefromstring(file_get_contents($src_file));
|
|
|
|
|
|
|
|
$dest = imagecreatetruecolor($width, $height);
|
|
|
|
imagefilledrectangle($dest, 0, 0, $width, $height, imagecolorallocate($dest, 0xFF, 0xFF, 0xFF));
|
|
|
|
|
|
|
|
$scale = max( $width/$src_width, $height/$src_height ); // overscale + crop
|
|
|
|
|
|
|
|
$box_w = $width/$scale;
|
|
|
|
$box_h = $height/$scale;
|
|
|
|
|
|
|
|
$box_xoff = floor(($src_width - $box_w)/2);
|
|
|
|
$box_yoff = floor(($src_height - $box_h)/2);
|
|
|
|
|
|
|
|
imagecopyresampled(
|
|
|
|
$dest, $im,
|
|
|
|
0, 0,
|
|
|
|
$box_xoff, $box_yoff,
|
|
|
|
$width, $height, $box_w, $box_h
|
|
|
|
);
|
|
|
|
|
|
|
|
imagedestroy($im);
|
|
|
|
|
|
|
|
if (is_null($dest_file)) {
|
|
|
|
return $dest;
|
|
|
|
} else {
|
|
|
|
return imagejpeg($dest, $dest_file);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
function mkspritesheet(array $handles, $dest_file, $width, $height) {
|
|
|
|
$im = imagecreatetruecolor($width, $height * count($handles));
|
|
|
|
|
|
|
|
for($i = 0, $e = count($handles); $i != $e; ++$i) {
|
|
|
|
imagecopy($im, $handles[$i], 0, $i * $height, 0, 0, $width, $height);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (is_null($dest_file)) {
|
|
|
|
return $dest_file;
|
|
|
|
} else {
|
|
|
|
return imagejpeg($im, $dest_file);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
function fbytes($size, $suffixes='B|KiB|MiB|GiB|TiB') {
|
|
|
|
$sxlist = explode('|', $suffixes);
|
|
|
|
if ($size < 1024) {
|
|
|
|
return $size.$sxlist[0];
|
|
|
|
}
|
|
|
|
|
|
|
|
while ($size > 1024 && count($sxlist) >= 2) {
|
|
|
|
array_shift($sxlist);
|
|
|
|
$size /= 1024;
|
|
|
|
}
|
2020-05-04 06:06:49 +00:00
|
|
|
return number_format($size, 2).' '.array_shift($sxlist);
|
2016-04-18 07:04:52 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
function str_ext($sz) {
|
|
|
|
$dpos = strrpos($sz, '.');
|
|
|
|
return substr($sz, $dpos+1);
|
|
|
|
}
|
|
|
|
|
|
|
|
function is_image($sz) {
|
|
|
|
return in_array(strtolower(str_ext($sz)), ['jpg', 'png', 'jpeg']);
|
|
|
|
}
|
|
|
|
|
|
|
|
function hesc($sz) {
|
|
|
|
return @htmlentities($sz, ENT_QUOTES | ENT_SUBSTITUTE, 'UTF-8');
|
|
|
|
}
|
|
|
|
|
2017-10-29 01:15:00 +00:00
|
|
|
function mkdir_all($path) {
|
|
|
|
$epath = escapeshellarg($path);
|
|
|
|
`mkdir -p ${epath}`;
|
|
|
|
}
|
|
|
|
|
2016-04-18 07:04:52 +00:00
|
|
|
function text2html($sz) {
|
|
|
|
|
|
|
|
$identity = function($sz) {
|
|
|
|
return $sz;
|
|
|
|
};
|
|
|
|
|
|
|
|
$splitInside = function($begin, $end, $sz) {
|
|
|
|
$parts = explode($begin, $sz);
|
|
|
|
if (count($parts) == 1) return [$sz];
|
|
|
|
|
|
|
|
$ret = [$parts[0]];
|
|
|
|
for($i = 1, $e = count($parts); $i !== $e; ++$i) {
|
|
|
|
$inner = explode($end, $parts[$i], 2);
|
|
|
|
$ret = array_merge($ret, $inner);
|
|
|
|
}
|
|
|
|
return $ret;
|
|
|
|
};
|
|
|
|
|
|
|
|
$oddEven = function(array $parts, $odd, $even, $join='') {
|
|
|
|
$ret = [];
|
|
|
|
for($i = 0, $e = count($parts); $i != $e; ++$i) {
|
|
|
|
$ret[] = ($i % 2) ? $odd($parts[$i]) : $even($parts[$i]);
|
|
|
|
}
|
|
|
|
return implode($join, $ret);
|
|
|
|
};
|
|
|
|
|
|
|
|
$sectionFmt = function($sz) use($oddEven, $identity) {
|
|
|
|
$base = hesc($sz);
|
|
|
|
|
|
|
|
$base = preg_replace('~^=+(.+)=+~m', '<strong>\\1</strong>', $base);
|
2017-04-23 06:42:01 +00:00
|
|
|
$base = preg_replace('~\\[url=([^\\]]+?)\\](.+?)\\[/url\\]~m', '<a href="\\1">\\2</a>', $base);
|
2018-12-30 01:35:49 +00:00
|
|
|
|
|
|
|
$base = preg_replace('~\\[([^\\]]+?)\\]\\((https?://.+?)\\)~m', '<a href="\\2">\\1</a>', $base); // Support markdown-style URLs
|
|
|
|
|
|
|
|
$base = preg_replace('~([^="])(https?://[^ \\r\\n\\t]+)~i', '\\1<a href="\\2">\\2</a>', $base); // Support standalone URLs
|
2016-04-18 07:04:52 +00:00
|
|
|
$base = preg_replace('~\\[b\\](.+?)\\[/b\\]~m', '<strong>\\1</strong>', $base);
|
|
|
|
$base = preg_replace('~\\[i\\](.+?)\\[/i\\]~m', '<i>\\1</i>', $base);
|
|
|
|
$base = preg_replace('~\\[spoiler\\](.+?)\\[/spoiler\\]~m', '<span class="spoiler">\\1</span>', $base);
|
|
|
|
$base = preg_replace('~\n- ~ms', "\n• ", $base);
|
|
|
|
|
2018-12-30 01:35:49 +00:00
|
|
|
$base = preg_replace('~^```.+$~m', '`', $base); // Convert ```html to single `{}` element
|
|
|
|
|
|
|
|
// TODO support markdown tables
|
|
|
|
|
2016-04-18 07:04:52 +00:00
|
|
|
$btparts = explode('`', $base);
|
|
|
|
if (count($btparts) > 1 && (count($btparts) % 2)) {
|
|
|
|
for ($i = 1, $e = count($btparts); $i < $e; $i += 2) {
|
|
|
|
$class = 'code';
|
|
|
|
if (strpos($btparts[$i], "\n") !== false) {
|
|
|
|
$class .= ' code-multiline';
|
|
|
|
}
|
2018-12-30 01:35:49 +00:00
|
|
|
$btparts[$i] = '<span class="'.$class.'">'.ltrim($btparts[$i], "\n").'</span>';
|
2016-04-18 07:04:52 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return $oddEven($btparts, $identity, 'nl2br');
|
|
|
|
};
|
|
|
|
|
|
|
|
$htmlSections = $splitInside('<html>', '</html>', $sz);
|
|
|
|
return $oddEven($htmlSections, $identity, $sectionFmt);
|
|
|
|
}
|
|
|
|
|
|
|
|
function array_decimate($array, $total, $partno) {
|
|
|
|
$ct = 0;
|
|
|
|
$ret = [];
|
|
|
|
foreach($array as $k => $v) {
|
|
|
|
if (++$ct % $total == ($partno - 1)) {
|
|
|
|
$ret[$k] = $v;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return $ret;
|
|
|
|
}
|