...

View Full Version : JSI; JavaScript Image Conversion Functions



Eternity Angel
12-24-2009, 05:45 AM
These are functions intended to be used with the JSI image format, an image type designed for manual editing, using JavaScript to display it. Further information can be found in the JavaScript thread here;

http://www.codingforums.com/showthread.php?t=185231



Convert a raw GD image to JSI or xJSI format;


function imagejsi($image,$format=0,$file="") {

/*****[ By Richard Moyer - v1.1 ]**************************************************************************

Takes a raw image and converts it into a JSI or xJSI image based on $format. If $file is specified,
then this function will output to it instead of returning the converted image. Returns false if the
raw image does not exist, or the $file cannot be opened/written to.


- $image = Raw image to be converted.
- $format = Set to 1 to convert the image into xJSI format.
- $file = The file, if specified, to save the image into. instead of returning it.

**************************************************************************************************** ******/

$trans_threshold = 114; // What transparency pixels are seen as transparent at (0 would convert all pixels to transparent, 64 would convert pixels that are 50% transparent into transparent, 127 would convert only truly 100% transparent pixels into the transparent color).
$maxpalette = 1296; // Maximum palette a JSI image can have. Do not change this.
$csize = ($format != 1) ? 3: 6; // The size of the HTML colors. JSI uses only 3 characters to represent color.
$width = @imagesx($image);
$height = @imagesy($image);
if (!$width || !$height || $width == 0 || $height == 0 || ($file != "" && !$fh = @fopen($file,'wb'))) return false;

// Set the variables used...
$colors = array();
$colors_used = array();
$transparent = "";
$guts = array();

// Figures out all of the used colors, storing the number into $colors_used, and the location data into $colors.
// Also sets the $guts of the image, which is used later for the actual palette locations for each pixel.
for ($y=0;$y<$height;$y++) {
$guts[$y] = array();
for ($x=0;$x<$width;$x++) {
$guts[$y][$x] = "";
$temp = imagecolorsforindex($image,imagecolorat($image,$x,$y));
if ($temp['alpha'] >= $trans_threshold) $temp2 = 'trans';
else {
$temp2 = strtoupper(str_pad(base_convert($temp['red'],10,16),2,"0",STR_PAD_LEFT).str_pad(base_convert($temp['green'],10,16),2,"0",STR_PAD_LEFT).str_pad(base_convert($temp['blue'],10,16),2,"0",STR_PAD_LEFT));
if ($format == 0) $temp2 = substr($temp2,0,1).substr($temp2,2,1).substr($temp2,4,1);
}
if (!isset($colors[$temp2])) {
$colors[$temp2] = array();
$colors_used[$temp2] = 0;
}
$colors[$temp2][] = $x.",".$y;
$colors_used[$temp2]++;
}
}
ksort($colors);
asort($colors_used,SORT_NUMERIC);

// Minimize palette for JSI images, in case the image has more than $maxpalette colors. xJSI doesn't need to be reduced.
$offs = 1;
$use = "";
while ($format == 0 && count($colors) > $maxpalette) {
$offs = ($use == "") ? 1: ($offs+1);
$use = "";
foreach ($colors_used as $key => $value) {
if ($use == "" && $key != "trans") {
$acceptable = ",";
$use = $key;
$rgb = array(base_convert(substr($use,0,1),16,10),base_convert(substr($use,1,1),16,10),base_convert(substr( $use,2,1),16,10));
}
else if ($key != "trans") {
$rgb = array(abs(base_convert(substr($use,0,1),16,10)-base_convert(substr($key,0,1),16,10)),abs(base_convert(substr($use,1,1),16,10)-base_convert(substr($key,1,1),16,10)),abs(base_convert(substr($use,2,1),16,10)-base_convert(substr($key,2,1),16,10)));
if ($rgb[0] <= $offs && $rgb[1] <= $offs && $rgb[2] <= $offs) {
foreach ($colors[$use] as $key2 => $value2) {
$colors[$key][] = $value2;
$colors_used[$key]++;
}
unset($colors[$use],$colors_used[$use]);
$use = "";
break;
}
}
}
}

// If there was any transparent color set, then find a usable palette color for it that won't conflict with the
// rest of the used palette.
if (isset($colors['trans'])) {
$count = 0;
$temp = str_repeat("0",$csize);
$stop = str_repeat("F",$csize);
while (isset($colors[$temp]) && $temp != $stop) {
$count++;
$temp = str_pad(base_convert($count,10,16),$csize,"0",STR_PAD_LEFT);
}
if ($temp != $stop) $transparent = $temp;
}

// Now create the image from the details we've already set above.
$zoom = ($format != 1) ? "1": "1-e1.0"; // The version is stored beside the zoom in the first entry of the image. JSI images won't work with xJSI, and vice versa.
$palette = "";
$guts = "";
$count = 0;
foreach ($colors as $key => $value) {
if ($key == "trans") $key = $transparent;
$palette .= $key;
foreach ($value as $key2 => $value2) {
$temp = explode(",",$value2);
$guts[$temp[1]][$temp[0]] = ($format != 1) ? str_pad(strtoupper(base_convert($count,10,36)),2,"0",STR_PAD_LEFT): strtoupper(base_convert($count,10,36));
}
$count++;
}

// Implode the $guts...
foreach ($guts as $key => $value) {
ksort($guts[$key],SORT_NUMERIC);
$guts[$key] = ($format != 1) ? implode("",$guts[$key]): implode(",",$guts[$key]);
}
ksort($guts,SORT_NUMERIC);
$guts = ($format != 1) ? implode("\t",$guts): implode("/",$guts); // JSI rows are separated by a tab, xJSI by a forward slash.

$res = $zoom."\t\t".$transparent."\t\t".$palette."\t\t".$guts;

// If $file was specified, we already opened the $fh in the if statement near the top, and checked it's openability.
if ($file != "") {
if (!fwrite($fh,$res)) return false;
fclose($fh);
return true;
}
return $res;
}



Convert an xJSI or JSI image to a raw GD image;


function imagecreatefromjsi($image="") {

/*****[ By Richard Moyer - v1.0 ]**************************************************************************

Takes a JSI or xJSI image and converts it to a raw format, returning it. If $image is a file, it
will load the image from there. Returns false if the JSI image is incorrectly formatted, or the JSI
image is of an unsupported version.


- $image = The text of the JSI image to be converted, or the path to the file to use.

**************************************************************************************************** ******/

// Define the extension functions we'll need for converting and verification.
if (!function_exists("JSIonlyHex")) {
function JSIonlyHex($inp) {
return preg_replace("/[^0-9a-f]/i","",$inp);
}
function JSIhex($a) {
$a = strtolower($a);
$set = "abcdef0123456789";
$result = "#";
for ($i=0;$i<strlen($a);$i++) {
if (strpos($set,substr($a,$i,1)) !== false) {
$result .= substr($a,$i,1);
}
if (strlen($result) >= 7) break;
}
while (strlen($result) < 7) {
$result .= "0";
}
$result = strtoupper($result);
return $result;
}
function JSIhex2rgb($col="#000000") {
$col = JSIhex($col);
$newr = base_convert("0x".substr($col,1,2),16,10);
$newg = base_convert("0x".substr($col,3,2),16,10);
$newb = base_convert("0x".substr($col,5,2),16,10);
return array($newr,$newg,$newb);
}
}

if ($image == "") return false;

// Check if $image is a file, and load it if so.
if (is_file($image)) $image = @file_get_contents($image);

// Run some verification.
$x = explode("\t\t",$image);
if (count($x) != 4) return false;
$format = 3;
$zoom = explode("-",$x[0]);
if (isset($zoom[1]) && substr($zoom[1],0,3) != "e1.") return false;
if (isset($zoom[1])) $format = 6;
$zoom = floor(abs($zoom[0]));
if ($zoom < 1) $zoom = 1;
if ($zoom > 99) $zoom = 99;
$transparent = JSIonlyHex($x[1]);
if (strlen($transparent) != 3 && strlen($transparent) != 6) $inv = "";
if (strlen($transparent) == 3) $transparent = substr($transparent,0,1).substr($transparent,0,1).substr($transparent,1,1).substr($transparent,1,1). substr($transparent,2,1).substr($transparent,2,1);
$temp = ($format == 3) ? explode("\t",$x[3]): explode("/",$x[3]);
if ($format == 3) $temp2 = (strlen($temp[0])/2);
else {
$temp2 = explode(",",$temp[0]);
$temp2 = count($temp2);
}

// Create our base image.
$img = imagecreatetruecolor(($temp2*$zoom),(count($temp)*$zoom));

// Define transparent color if it exists.
if ($transparent != "") {
$transparent = JSIhex2rgb(JSIhex($transparent));
$transparent = imagecolorallocate($img,$transparent[0],$transparent[1],$transparent[2]);
imagecolortransparent($img,$transparent);
}

// Create the palette.
$x[2] = JSIonlyHex($x[2]);
$maxp = (strlen($x[2])/$format);
$p = array();
$_i = 0;
if ((strlen($x[2])%$format) != 0) return false;
for ($i=0;$i<strlen($x[2]);$i=($i+$format)) {
$temp2 = substr($x[2],$i,$format);
if ($format == 3) $temp2 = substr($temp2,0,1).substr($temp2,0,1).substr($temp2,1,1).substr($temp2,1,1).substr($temp2,2,1).subst r($temp2,2,1);
$temp2 = JSIhex2rgb($temp2);
$p[$_i] = imagecolorallocate($img,$temp2[0],$temp2[1],$temp2[2]);
$_i++;
}

// Run through the image, drawing each pixel individually.
$xpos = 0;
$ypos = 0;
foreach ($temp as $key => $value) {
$xpos = 0;
if ($format == 3) {
for ($i=0;$i<strlen($value);$i=($i+2)) {
$temp2 = base_convert(substr($value,$i,2),36,10);
if ($temp2 >= $maxp) {
imagedestroy($img);
return false;
}
imagefilledrectangle($img,$xpos,$ypos,($xpos+($zoom-1)),($ypos+($zoom-1)),$p[$temp2]);
$xpos = ($xpos+$zoom);
}
}
else {
$temp3 = explode(",",$value);
foreach ($temp3 as $key2 => $value2) {
$temp2 = base_convert($value2,36,10);
if ($temp2 >= $maxp) {
imagedestroy($img);
return false;
}
imagefilledrectangle($img,$xpos,$ypos,($xpos+($zoom-1)),($ypos+($zoom-1)),$p[$temp2]);
$xpos = ($xpos+$zoom);
}
}
$ypos = ($ypos+$zoom);
}
return $img;
}

track9200
09-07-2010, 04:46 PM
thanks for handy piece of code, here is also useful thread for php based conversion -
http://www.codingforums.com/archive/index.php/t-69695.htmlchat programs (http://www.flashcoms.com)

wincode
09-08-2010, 07:48 AM
This looks interesting. I'm kinda new.. what are some uses of the JSI?

Also there's no game on the fantasian kingdoms site :(

BennoM1984
06-01-2011, 01:02 PM
wow,

i googled the whole www for that piece of code....
thank you so so much :)))))))

regards

benno

devonssmart
07-15-2011, 06:10 PM
Thank you for the code.. :thumbsup:



EZ Archive Ads Plugin for vBulletin Copyright 2006 Computer Help Forum