added ArduboyFx begin drawBitmap and display to the crate also added a fxdata-converter.html file to the docs

This commit is contained in:
ZennDev1337 2023-10-03 08:50:48 +02:00
parent 9248c9f2ac
commit ddf419f702
10 changed files with 3218 additions and 2682 deletions

View file

@ -2,6 +2,7 @@
#![allow(non_upper_case_globals)] #![allow(non_upper_case_globals)]
//Include the Arduboy Library //Include the Arduboy Library
use arduboy_rust::arduboyfx::*;
#[allow(unused_imports)] #[allow(unused_imports)]
use arduboy_rust::prelude::*; use arduboy_rust::prelude::*;
@ -11,14 +12,23 @@ const arduboy: Arduboy2 = Arduboy2::new();
// Progmem data // Progmem data
// dynamic ram variables // dynamic ram variables
const FX_DATA_PAGE: u16 = 0xffff;
const FX_DATA_BYTES: u32 = 234;
const FXlogo: u32 = 0x000000;
const FXlogoWith: i16 = 115;
const FXlogoHeight: i16 = 16;
static mut x: i16 = (WIDTH - FXlogoWith) / 2;
static mut y: i16 = 25;
static mut xDir: i8 = 1;
static mut yDir: i8 = 1;
// The setup() function runs once when you turn your Arduboy on // The setup() function runs once when you turn your Arduboy on
#[no_mangle] #[no_mangle]
pub unsafe extern "C" fn setup() { pub unsafe extern "C" fn setup() {
// put your setup code here, to run once: // put your setup code here, to run once:
arduboy.begin(); arduboy.begin();
arduboy.set_frame_rate(30); arduboy.set_frame_rate(30);
arduboy.clear(); arduboyfx_begin_data(FX_DATA_PAGE);
} }
// The loop() function repeats forever after setup() is done // The loop() function repeats forever after setup() is done
#[no_mangle] #[no_mangle]
@ -28,5 +38,14 @@ pub unsafe extern "C" fn loop_() {
if !arduboy.next_frame() { if !arduboy.next_frame() {
return; return;
} }
arduboy.display(); arduboyfx_draw_bitmap(x, y, FXlogo, 0, 0);
x += xDir as i16;
y += yDir as i16;
if x == 0 || x == WIDTH - FXlogoWith {
xDir = -xDir;
}
if y == 0 || y == HEIGHT - FXlogoHeight {
yDir = -yDir;
}
arduboyfx_display_clear();
} }

View file

@ -37,5 +37,6 @@ pub use crate::library::arduboy_tone::{self, ArduboyTones};
pub use crate::library::ardvoice::{self, ArdVoice}; pub use crate::library::ardvoice::{self, ArdVoice};
pub use crate::library::eeprom::{EEPROM, EEPROMBYTE}; pub use crate::library::eeprom::{EEPROM, EEPROMBYTE};
pub use crate::library::{arduino, c, sprites}; pub use crate::library::{arduino, c, sprites};
pub use crate::library::arduboyfx;
pub mod serial_print; pub mod serial_print;

View file

@ -14,11 +14,11 @@ pub const FONT_SIZE: u8 = 6;
/// The standard width of the arduboy /// The standard width of the arduboy
/// ///
/// this is to calculate with it. /// this is to calculate with it.
pub const WIDTH: u8 = 128; pub const WIDTH: i16 = 128;
/// The standard height of the arduboy /// The standard height of the arduboy
/// ///
/// this is to calculate with it. /// this is to calculate with it.
pub const HEIGHT: u8 = 64; pub const HEIGHT: i16 = 64;
/// This item is to chose between Black or White /// This item is to chose between Black or White
#[derive(Debug, Copy, Clone, Hash, Eq, PartialEq, Ord, PartialOrd)] #[derive(Debug, Copy, Clone, Hash, Eq, PartialEq, Ord, PartialOrd)]

View file

@ -1,8 +1,26 @@
#![allow(non_upper_case_globals)]
use core::ffi::{c_int, c_long, c_uchar, c_uint, c_ulong};
pub const dbmNormal: u8 = 0;
pub const dbmOverwrite: u8 = 0;
pub const dbmMasked: u8 = 1;
extern "C" { extern "C" {
#[link_name = "arduboyfx_begin"] #[link_name = "arduboyfx_begin"]
fn arduboyfx_begin(); pub fn arduboyfx_begin();
#[link_name = "arduboyfx_begin_data"]
} pub fn arduboyfx_begin_data(datapage: c_uint);
#[link_name = "arduboyfx_begin_data_save"]
pub fn arduboyfx_begin_data_save(datapage: c_uint, savepage: c_uint);
#[link_name = "arduboyfx_display"]
pub fn arduboyfx_display();
#[link_name = "arduboyfx_display_clear"]
pub fn arduboyfx_display_clear();
#[link_name = "arduboyfx_draw_bitmap"]
pub fn arduboyfx_draw_bitmap(
x: c_int,
y: c_int,
address: c_ulong,
frame: c_uchar,
mode: c_uchar,
);
}

View file

@ -100,7 +100,6 @@
.topnav { .topnav {
background-color: #000000; background-color: #000000;
overflow: hidden;
height: 47px; height: 47px;
} }
@ -126,7 +125,7 @@
display: none; display: none;
} }
@media screen and (max-width: 1049px) { @media screen and (max-width: 800px) {
.topnav a:not(:first-child) { .topnav a:not(:first-child) {
display: none; display: none;
} }
@ -137,10 +136,10 @@
} }
} }
@media screen and (max-width: 1049px) { @media screen and (max-width: 800px) {
.topnav.responsive { .topnav.responsive {
position: relative; position: relative;
height: 247px; height: auto;
} }
.topnav { .topnav {
@ -215,13 +214,31 @@
</style> </style>
<div class="wrapper"> <div class="wrapper">
<div class="topnav" id="myTopnav"> <div class="topnav" id="myTopnav">
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html">Rust for Arduboy</a> <a
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html">Image href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html"
Converter</a> ><nobr>Rust for Arduboy</nobr></a
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html">Tile Converter</a> >
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html">Sprite Converter</a> <a
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html" class="active">.arduboy href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html"
Generator</a> ><nobr>Image Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html"
><nobr>Tile Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html"
><nobr>Sprite Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html" class="active"
><nobr>.arduboy Generator</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/fxdata-converter.html"
><nobr>fxdata.h Converter</nobr></a
>
<a href="javascript:void(0);" class="icon" onclick="myFunction()"> <a href="javascript:void(0);" class="icon" onclick="myFunction()">
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-list" <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-list"
viewBox="0 0 16 16"> viewBox="0 0 16 16">

363
docs/fxdata-converter.html Normal file
View file

@ -0,0 +1,363 @@
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link
rel="icon"
href="https://upload.wikimedia.org/wikipedia/commons/0/0f/Original_Ferris.svg"
type="image/svg+xml"
/>
<title>ZennDev1337 Image Converter</title>
</head>
<body onload="setup(this);">
<style>
html,
body {
margin: 0;
background-color: black;
color: azure;
overflow: hidden;
}
body {
font-family: Courier New;
text-align: center;
align-items: center;
font-size: xx-large;
font-weight: 700;
}
.wrapper {
min-height: calc(100vh - 50px);
}
.footer {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 600;
height: 50px;
color: #e7e7e7;
}
.footer > a {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 700;
margin: 0;
color: #e7e7e7;
text-decoration: none;
}
.sticky {
bottom: 0;
height: 50px;
}
textarea {
background-color: #281c1c;
color: azure;
border: dotted 2px #ce422b;
width: 670px;
height: 300px;
resize: none;
}
.title > p {
padding-left: 20px;
margin: 0;
padding-right: 20px;
color: #e7e7e7;
font-size: xx-large;
}
.title {
padding-top: 50px;
}
.separator {
border-top: solid #281c1c;
border-bottom: none;
border-left: none;
border-right: none;
margin-top: 40px;
width: clamp(700px, 70vw, 1200px);
}
.image-container {
margin-top: 40px;
min-height: 80px;
}
p {
font-size: medium;
}
.txtHead {
margin-bottom: 5px;
}
.topnav {
background-color: #000000;
height: 47px;
}
.topnav a {
color: #f2f2f2;
text-align: center;
padding: 14px 16px;
text-decoration: none;
font-size: 17px;
}
.topnav a:hover {
background-color: #ddd;
color: black;
}
.topnav a.active {
background-color: #281c1c;
color: white;
}
.topnav .icon {
display: none;
}
@media screen and (max-width: 800px) {
.topnav a:not(:first-child) {
display: none;
}
.topnav a.icon {
float: right;
display: block;
}
}
@media screen and (max-width: 800px) {
.topnav.responsive {
position: relative;
height: auto;
}
.topnav {
text-align: left;
}
.topnav.responsive a.icon {
position: absolute;
right: 0;
top: 0;
}
.topnav.responsive a {
float: none;
display: block;
text-align: left;
}
}
</style>
<div class="wrapper">
<div class="topnav" id="myTopnav">
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html"
><nobr>Rust for Arduboy</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html"
><nobr>Image Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html"
><nobr>Tile Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html"
><nobr>Sprite Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html"
><nobr>.arduboy Generator</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/fxdata-converter.html"
class="active"
><nobr>fxdata.h Converter</nobr></a
>
<a
href="javascript:void(0);"
class="icon"
onclick="myFunction()"
>
<svg
xmlns="http://www.w3.org/2000/svg"
width="16"
height="16"
fill="currentColor"
class="bi bi-list"
viewBox="0 0 16 16"
>
<path
fill-rule="evenodd"
d="M2.5 12a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5z"
/>
</svg>
</a>
</div>
<div class="title">
<p>Drop your fxdata.h here</p>
</div>
<hr class="separator" />
<div class="image-container">
<div id="image-container"></div>
</div>
<hr class="separator" />
</div>
<footer class="footer">
<a href="https://github.com/ZennDev1337/" target="_blank"
>By ZennDev1337</a
>
</footer>
<script language="JavaScript">
function myFunction() {
var x = document.getElementById("myTopnav");
if (x.className === "topnav") {
x.className += " responsive";
} else {
x.className = "topnav";
}
}
</script>
<script language="JavaScript">
function swapImage(t, e) {
var r = t.getAttribute("data-srcnm");
t.removeAttribute("srcset"),
r || t.setAttribute("data-srcnm", t.src),
(t.src = e);
}
function setOriginal(t) {
var e = "",
r = "";
(r = t.getAttribute("data-srcmd")),
(e = t.getAttribute("data-srcnm")),
r
? ((t.src = r), t.removeAttribute("data-srcmd"))
: ((t.src = e), t.removeAttribute("data-srcnm"));
}
function swapImageMD(t, e) {
t.setAttribute("data-srcmd", t.src), (t.src = e);
}
function jsready(t) {
/in/.test(document.readyState)
? setTimeout("jsready(" + t + ")", 9)
: t();
}
jsready(function () {
var t = window.devicePixelRatio ? window.devicePixelRatio : 1;
if (t > 1)
for (
var e = document.getElementsByTagName("img"), r = 0;
r < e.length;
r++
)
e[r].getAttribute("data-src2x") &&
(e[r].setAttribute(
"data-src-orig",
e[r].getAttribute("src")
),
e[r].setAttribute(
"src",
e[r].getAttribute("data-src2x")
));
});
function setup(body) {
body.ondragover = function () {
return false;
};
body.ondragend = function () {
return false;
};
body.ondrop = function (e) {
// Prevent the browser from showing the dropped file
e.preventDefault();
// Get the image data
var reader = new FileReader();
reader.onload = function (e) {
//console.log(this.result);
convertCtoRust(this.result);
};
reader.readAsText(e.dataTransfer.files[0]);
// var imageData = getImageData(e);
// // If there is some data, add it to the page
// if (imageData !== null) {
// addDroppedElement(imageData);
// }
};
}
function convertCtoRust(file) {
var lines = file.split("\n");
var resultString = "";
var droppedImageCode = document.createElement("textarea");
droppedImageCode.className = "code";
droppedImageCode.style.width = "698px";
droppedImageCode.rows = "20";
var imageContainer = document.getElementById("image-container");
imageContainer.innerHTML = "";
imageContainer.appendChild(droppedImageCode);
var regexPattern = /\s+/g;
for (var line of lines) {
if (!line) {
resultString += "\n";
}
if (line.includes("//")) {
resultString += `${line.replace(regexPattern, " ")}\n`;
}
if (line.includes("/***")) {
var words = line.split(" ");
words.pop();
words.shift();
resultString += `// ${words}\n// Convertet to Rust with https://zenndev1337.github.io/Rust-for-Arduboy/fxdata-converter.html`;
}
if (line.includes("constexpr")) {
var words = line.replace(regexPattern, " ").split(" ");
for (i in words) {
if (words[i] === "") delete words[i];
}
var type = "";
var cType = words[1];
switch (cType) {
case "uint16_t":
type = "u16";
break;
case "uint24_t":
type = "u32";
break;
case "uint32_t":
type = "u32";
break;
case "uint8_t":
type = "u8";
break;
default:
type = "???";
}
resultString += `const ${words[2]}:${type} = ${words[4]}\n`;
}
}
var result = resultString.split("\n");
result.shift();
resultString = result.join("\n");
droppedImageCode.innerHTML = resultString;
}
</script>
</body>
</html>

View file

@ -1,403 +1,435 @@
<!DOCTYPE html> <!DOCTYPE html>
<html> <html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link
rel="icon"
href="https://upload.wikimedia.org/wikipedia/commons/0/0f/Original_Ferris.svg"
type="image/svg+xml"
/>
<title>ZennDev1337 Image Converter</title>
</head>
<head> <body onload="setup(this);">
<meta name="viewport" content="width=device-width, initial-scale=1.0"> <style>
<link rel="icon" href="https://upload.wikimedia.org/wikipedia/commons/0/0f/Original_Ferris.svg" html,
type="image/svg+xml" /> body {
<title>ZennDev1337 Image Converter</title> margin: 0;
</head> background-color: black;
color: azure;
<body onload="setup(this);"> overflow: hidden;
<style>
html,
body {
margin: 0;
background-color: black;
color: azure;
overflow: hidden;
}
body {
font-family: Courier New;
text-align: center;
align-items: center;
font-size: xx-large;
font-weight: 700;
}
.wrapper {
min-height: calc(100vh - 50px);
}
.footer {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 600;
height: 50px;
color: #e7e7e7;
}
.footer>a {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 700;
margin: 0;
color: #e7e7e7;
text-decoration: none;
}
.sticky {
bottom: 0;
height: 50px;
}
textarea {
background-color: #281c1c;
color: azure;
border: dotted 2px #ce422b;
width: 670px;
height: 300px;
resize: none;
}
.title>p {
padding-left: 20px;
margin: 0;
padding-right: 20px;
color: #e7e7e7;
font-size: xx-large;
}
.title {
padding-top: 50px;
}
.separator {
border-top: solid #281c1c;
border-bottom: none;
border-left: none;
border-right: none;
margin-top: 40px;
width: clamp(700px, 70vw, 1200px);
}
.image-container {
margin-top: 40px;
min-height: 80px;
}
p {
font-size: medium;
}
.txtHead {
margin-bottom: 5px;
}
.topnav {
background-color: #000000;
overflow: hidden;
height: 47px;
}
.topnav a {
color: #f2f2f2;
text-align: center;
padding: 14px 16px;
text-decoration: none;
font-size: 17px;
}
.topnav a:hover {
background-color: #ddd;
color: black;
}
.topnav a.active {
background-color: #281c1c;
color: white;
}
.topnav .icon {
display: none;
}
@media screen and (max-width: 1049px) {
.topnav a:not(:first-child) {
display: none;
} }
.topnav a.icon { body {
float: right; font-family: Courier New;
display: block; text-align: center;
align-items: center;
font-size: xx-large;
font-weight: 700;
} }
}
@media screen and (max-width: 1049px) { .wrapper {
.topnav.responsive { min-height: calc(100vh - 50px);
position: relative; }
height: 247px;
.footer {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 600;
height: 50px;
color: #e7e7e7;
}
.footer > a {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 700;
margin: 0;
color: #e7e7e7;
text-decoration: none;
}
.sticky {
bottom: 0;
height: 50px;
}
textarea {
background-color: #281c1c;
color: azure;
border: dotted 2px #ce422b;
width: 670px;
height: 300px;
resize: none;
}
.title > p {
padding-left: 20px;
margin: 0;
padding-right: 20px;
color: #e7e7e7;
font-size: xx-large;
}
.title {
padding-top: 50px;
}
.separator {
border-top: solid #281c1c;
border-bottom: none;
border-left: none;
border-right: none;
margin-top: 40px;
width: clamp(700px, 70vw, 1200px);
}
.image-container {
margin-top: 40px;
min-height: 80px;
}
p {
font-size: medium;
}
.txtHead {
margin-bottom: 5px;
} }
.topnav { .topnav {
text-align: left; background-color: #000000;
height: 47px;
} }
.topnav.responsive a.icon { .topnav a {
position: absolute; color: #f2f2f2;
right: 0; text-align: center;
top: 0; padding: 14px 16px;
text-decoration: none;
font-size: 17px;
} }
.topnav.responsive a { .topnav a:hover {
float: none; background-color: #ddd;
display: block; color: black;
text-align: left;
} }
}
</style>
<div class="wrapper">
<div class="topnav" id="myTopnav">
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html">Rust for Arduboy</a>
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html" class="active">Image
Converter</a>
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html">Tile Converter</a>
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html">Sprite Converter</a>
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html">.arduboy
Generator</a>
<a href="javascript:void(0);" class="icon" onclick="myFunction()">
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-list"
viewBox="0 0 16 16">
<path fill-rule="evenodd"
d="M2.5 12a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5z" />
</svg>
</a>
</div>
<div class="title">
<p>Drop your image here</p>
</div>
<hr class="separator" />
<div class="image-container">
<div id="image-container"></div>
</div>
<hr class="separator" />
</div>
<footer class="footer"> .topnav a.active {
<a href="https://github.com/ZennDev1337/" target="_blank">By ZennDev1337</a> background-color: #281c1c;
</footer> color: white;
<script language="JavaScript">
function myFunction() {
var x = document.getElementById("myTopnav");
if (x.className === "topnav") {
x.className += " responsive";
} else {
x.className = "topnav";
} }
}
</script> .topnav .icon {
<script language="JavaScript"> display: none;
function swapImage(t, e) { }
var r = t.getAttribute("data-srcnm");
t.removeAttribute("srcset"), @media screen and (max-width: 800px) {
r || t.setAttribute("data-srcnm", t.src), .topnav a:not(:first-child) {
(t.src = e); display: none;
} }
function setOriginal(t) {
var e = "", .topnav a.icon {
r = ""; float: right;
(r = t.getAttribute("data-srcmd")), display: block;
(e = t.getAttribute("data-srcnm")), }
r }
? ((t.src = r), t.removeAttribute("data-srcmd"))
: ((t.src = e), t.removeAttribute("data-srcnm")); @media screen and (max-width: 800px) {
} .topnav.responsive {
function swapImageMD(t, e) { position: relative;
t.setAttribute("data-srcmd", t.src), (t.src = e); height: auto;
} }
function jsready(t) {
/in/.test(document.readyState) .topnav {
? setTimeout("jsready(" + t + ")", 9) text-align: left;
: t(); }
}
jsready(function () { .topnav.responsive a.icon {
var t = window.devicePixelRatio ? window.devicePixelRatio : 1; position: absolute;
if (t > 1) right: 0;
for ( top: 0;
var e = document.getElementsByTagName("img"), r = 0; }
r < e.length;
r++ .topnav.responsive a {
) float: none;
e[r].getAttribute("data-src2x") && display: block;
(e[r].setAttribute( text-align: left;
"data-src-orig", }
e[r].getAttribute("src") }
), </style>
<div class="wrapper">
<div class="topnav" id="myTopnav">
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html"
><nobr>Rust for Arduboy</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html"
class="active"
><nobr>Image Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html"
><nobr>Tile Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html"
><nobr>Sprite Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html"
><nobr>.arduboy Generator</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/fxdata-converter.html"
><nobr>fxdata.h Converter</nobr></a
>
<a
href="javascript:void(0);"
class="icon"
onclick="myFunction()"
>
<svg
xmlns="http://www.w3.org/2000/svg"
width="16"
height="16"
fill="currentColor"
class="bi bi-list"
viewBox="0 0 16 16"
>
<path
fill-rule="evenodd"
d="M2.5 12a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5z"
/>
</svg>
</a>
</div>
<div class="title">
<p>Drop your image here</p>
</div>
<hr class="separator" />
<div class="image-container">
<div id="image-container"></div>
</div>
<hr class="separator" />
</div>
<footer class="footer">
<a href="https://github.com/ZennDev1337/" target="_blank"
>By ZennDev1337</a
>
</footer>
<script language="JavaScript">
function myFunction() {
var x = document.getElementById("myTopnav");
if (x.className === "topnav") {
x.className += " responsive";
} else {
x.className = "topnav";
}
}
</script>
<script language="JavaScript">
function swapImage(t, e) {
var r = t.getAttribute("data-srcnm");
t.removeAttribute("srcset"),
r || t.setAttribute("data-srcnm", t.src),
(t.src = e);
}
function setOriginal(t) {
var e = "",
r = "";
(r = t.getAttribute("data-srcmd")),
(e = t.getAttribute("data-srcnm")),
r
? ((t.src = r), t.removeAttribute("data-srcmd"))
: ((t.src = e), t.removeAttribute("data-srcnm"));
}
function swapImageMD(t, e) {
t.setAttribute("data-srcmd", t.src), (t.src = e);
}
function jsready(t) {
/in/.test(document.readyState)
? setTimeout("jsready(" + t + ")", 9)
: t();
}
jsready(function () {
var t = window.devicePixelRatio ? window.devicePixelRatio : 1;
if (t > 1)
for (
var e = document.getElementsByTagName("img"), r = 0;
r < e.length;
r++
)
e[r].getAttribute("data-src2x") &&
(e[r].setAttribute(
"data-src-orig",
e[r].getAttribute("src")
),
e[r].setAttribute( e[r].setAttribute(
"src", "src",
e[r].getAttribute("data-src2x") e[r].getAttribute("data-src2x")
)); ));
}); });
function setup(body) { function setup(body) {
body.ondragover = function () { body.ondragover = function () {
return false; return false;
}; };
body.ondragend = function () { body.ondragend = function () {
return false; return false;
}; };
body.ondrop = function (e) { body.ondrop = function (e) {
// Prevent the browser from showing the dropped file // Prevent the browser from showing the dropped file
e.preventDefault(); e.preventDefault();
// Get the image data // Get the image data
var imageData = getImageData(e); var imageData = getImageData(e);
// If there is some data, add it to the page // If there is some data, add it to the page
if (imageData !== null) { if (imageData !== null) {
addDroppedElement(imageData); addDroppedElement(imageData);
}
};
}
function getImageData(event) {
var file = event.dataTransfer.files[0];
if (file.type.indexOf("image") === 0) {
return file;
}
}
function addDroppedElement(imageData) {
var reader = new FileReader();
reader.onload = function (event) {
event.preventDefault;
// Create image element
var droppedImage = new Image();
droppedImage.src = event.target.result;
// add delay so the image can be loaded properly before accessing it
setTimeout(function () {
// Create canvas for image
var droppedImageCanvas =
document.createElement("canvas");
droppedImageCanvas.width = droppedImage.naturalWidth;
droppedImageCanvas.height = droppedImage.naturalHeight;
// Create code container
var droppedImageCode =
document.createElement("textarea");
droppedImageCode.className = "code";
droppedImageCode.style.width = "698px";
droppedImageCode.rows = "20";
// Create div container
var droppedImageDiv = document.createElement("div");
droppedImageDiv.className = "image-view";
droppedImageDiv.appendChild(droppedImageCanvas);
var imageContainer =
document.getElementById("image-container");
imageContainer.innerHTML = "";
imageContainer.appendChild(droppedImageDiv);
imageContainer.appendChild(
document.createElement("br")
);
imageContainer.appendChild(droppedImageCode);
// Create context for drawing
var droppedImageContext =
droppedImageCanvas.getContext("2d");
// Draw the image
droppedImageContext.drawImage(droppedImage, 0, 0);
// Generate the sprite string
var spriteString =
"static " +
imageData.name.split(/_|\./)[0] +
": [u8;_] = " +
"[\n" +
droppedImage.naturalWidth +
", " +
droppedImage.naturalHeight +
", // width, height,\n";
var pageCount = Math.ceil(
droppedImage.naturalHeight / 8
);
var columnCount = droppedImage.naturalWidth;
var currentByte = 0;
// Read the sprite page-by-page
for (var page = 0; page < pageCount; page++) {
// Read the page column-by-column
for (
var column = 0;
column < columnCount;
column++
) {
// Read the column into a byte
var spriteByte = 0;
for (var yPixel = 0; yPixel < 8; yPixel++) {
// If the color of the pixel is not black, count it as white
var pixelColor =
droppedImageContext.getImageData(
column,
page * 8 + yPixel,
1,
1
).data;
if (
pixelColor[0] > 0 ||
pixelColor[1] > 0 ||
pixelColor[2] > 0
) {
spriteByte |= 1 << yPixel;
}
}
// Print the column in hex notation, add a comma for formatting
var digitStr = spriteByte.toString(16);
if (digitStr.length == 1) {
digitStr = "0" + digitStr;
}
spriteString += "0x" + digitStr + ", ";
if (
currentByte % droppedImage.naturalWidth ==
droppedImage.naturalWidth - 1
) {
spriteString += "\n";
}
currentByte++;
}
} }
// Terminate the array };
spriteString += "];"; }
// Create an invisible element containing the string function getImageData(event) {
droppedImageCode.innerHTML = spriteString; var file = event.dataTransfer.files[0];
if (file.type.indexOf("image") === 0) {
return file;
}
}
function addDroppedElement(imageData) {
var reader = new FileReader();
reader.onload = function (event) {
event.preventDefault;
// Resize canvas to show 2x scaled image // Create image element
droppedImageCanvas.width = var droppedImage = new Image();
droppedImage.naturalWidth * 2; droppedImage.src = event.target.result;
droppedImageCanvas.height = // add delay so the image can be loaded properly before accessing it
droppedImage.naturalHeight * 2; setTimeout(function () {
droppedImageContext = // Create canvas for image
droppedImageCanvas.getContext("2d"); var droppedImageCanvas =
droppedImageContext.imageSmoothingEnabled = false; document.createElement("canvas");
droppedImageContext.drawImage( droppedImageCanvas.width = droppedImage.naturalWidth;
droppedImage, droppedImageCanvas.height = droppedImage.naturalHeight;
0,
0,
droppedImage.naturalWidth * 2,
droppedImage.naturalHeight * 2
);
}, 50);
};
reader.readAsDataURL(imageData);
}
</script>
</body>
</html> // Create code container
var droppedImageCode =
document.createElement("textarea");
droppedImageCode.className = "code";
droppedImageCode.style.width = "698px";
droppedImageCode.rows = "20";
// Create div container
var droppedImageDiv = document.createElement("div");
droppedImageDiv.className = "image-view";
droppedImageDiv.appendChild(droppedImageCanvas);
var imageContainer =
document.getElementById("image-container");
imageContainer.innerHTML = "";
imageContainer.appendChild(droppedImageDiv);
imageContainer.appendChild(
document.createElement("br")
);
imageContainer.appendChild(droppedImageCode);
// Create context for drawing
var droppedImageContext =
droppedImageCanvas.getContext("2d");
// Draw the image
droppedImageContext.drawImage(droppedImage, 0, 0);
// Generate the sprite string
var spriteString =
"static " +
imageData.name.split(/_|\./)[0] +
": [u8;_] = " +
"[\n" +
droppedImage.naturalWidth +
", " +
droppedImage.naturalHeight +
", // width, height,\n";
var pageCount = Math.ceil(
droppedImage.naturalHeight / 8
);
var columnCount = droppedImage.naturalWidth;
var currentByte = 0;
// Read the sprite page-by-page
for (var page = 0; page < pageCount; page++) {
// Read the page column-by-column
for (
var column = 0;
column < columnCount;
column++
) {
// Read the column into a byte
var spriteByte = 0;
for (var yPixel = 0; yPixel < 8; yPixel++) {
// If the color of the pixel is not black, count it as white
var pixelColor =
droppedImageContext.getImageData(
column,
page * 8 + yPixel,
1,
1
).data;
if (
pixelColor[0] > 0 ||
pixelColor[1] > 0 ||
pixelColor[2] > 0
) {
spriteByte |= 1 << yPixel;
}
}
// Print the column in hex notation, add a comma for formatting
var digitStr = spriteByte.toString(16);
if (digitStr.length == 1) {
digitStr = "0" + digitStr;
}
spriteString += "0x" + digitStr + ", ";
if (
currentByte % droppedImage.naturalWidth ==
droppedImage.naturalWidth - 1
) {
spriteString += "\n";
}
currentByte++;
}
}
// Terminate the array
spriteString += "];";
// Create an invisible element containing the string
droppedImageCode.innerHTML = spriteString;
// Resize canvas to show 2x scaled image
droppedImageCanvas.width =
droppedImage.naturalWidth * 2;
droppedImageCanvas.height =
droppedImage.naturalHeight * 2;
droppedImageContext =
droppedImageCanvas.getContext("2d");
droppedImageContext.imageSmoothingEnabled = false;
droppedImageContext.drawImage(
droppedImage,
0,
0,
droppedImage.naturalWidth * 2,
droppedImage.naturalHeight * 2
);
}, 50);
};
reader.readAsDataURL(imageData);
}
</script>
</body>
</html>

View file

@ -99,8 +99,7 @@
.topnav { .topnav {
background-color: #000000; background-color: #000000;
overflow: hidden; min-height: 47px;
height: 47px;
} }
.topnav a { .topnav a {
@ -125,7 +124,7 @@
display: none; display: none;
} }
@media screen and (max-width: 1049px) { @media screen and (max-width: 800px) {
.topnav a:not(:first-child) { .topnav a:not(:first-child) {
display: none; display: none;
} }
@ -136,10 +135,10 @@
} }
} }
@media screen and (max-width: 1049px) { @media screen and (max-width: 800px) {
.topnav.responsive { .topnav.responsive {
position: relative; position: relative;
height: 247px; height: auto;
} }
.topnav { .topnav {
@ -167,12 +166,31 @@
</style> </style>
<div class="wrapper"> <div class="wrapper">
<div class="topnav" id="myTopnav"> <div class="topnav" id="myTopnav">
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html" class="active">Rust for Arduboy</a> <a
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html">Image Converter</a> href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html" class="active"
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html">Tile Converter</a> ><nobr>Rust for Arduboy</nobr></a
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html">Sprite Converter</a> >
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html">.arduboy <a
Generator</a> href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html"
><nobr>Image Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html"
><nobr>Tile Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html"
><nobr>Sprite Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html"
><nobr>.arduboy Generator</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/fxdata-converter.html"
><nobr>fxdata.h Converter</nobr></a
>
<a href="javascript:void(0);" class="icon" onclick="myFunction()"> <a href="javascript:void(0);" class="icon" onclick="myFunction()">
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-list" <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-list"
viewBox="0 0 16 16"> viewBox="0 0 16 16">

File diff suppressed because it is too large Load diff

View file

@ -1,489 +1,523 @@
<!DOCTYPE html> <!DOCTYPE html>
<html> <html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link
rel="icon"
href="https://upload.wikimedia.org/wikipedia/commons/0/0f/Original_Ferris.svg"
type="image/svg+xml"
/>
<title>ZennDev1337 Tile Converter</title>
</head>
<head> <body onload="setup(this);">
<meta name="viewport" content="width=device-width, initial-scale=1.0"> <style>
<link rel="icon" href="https://upload.wikimedia.org/wikipedia/commons/0/0f/Original_Ferris.svg" html,
type="image/svg+xml" /> body {
<title>ZennDev1337 Tile Converter</title> margin: 0;
</head> background-color: black;
color: azure;
<body onload="setup(this);"> overflow: hidden;
<style>
html,
body {
margin: 0;
background-color: black;
color: azure;
}
body {
font-family: Courier New;
text-align: center;
font-size: xx-large;
font-weight: 700;
}
.wrapper {
min-height: calc(100vh - 50px);
}
.footer {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 600;
height: 50px;
color: #e7e7e7;
}
.footer>a {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 700;
margin: 0;
color: #e7e7e7;
text-decoration: none;
}
.sticky {
bottom: 0;
height: 50px;
}
textarea {
background-color: #281c1c;
color: azure;
border: dotted 2px #ce422b;
width: 670px;
height: 300px;
resize: none;
}
.title>p {
padding-left: 20px;
margin: 0;
padding-right: 20px;
color: #e7e7e7;
font-size: xx-large;
}
.title {
padding-top: 50px;
}
.separator {
border-top: solid #281c1c;
border-bottom: none;
border-left: none;
border-right: none;
margin-top: 40px;
width: clamp(700px, 70vw, 1200px);
}
.image-container {
margin-top: 40px;
min-height: 80px;
}
p {
font-size: medium;
}
.txtHead {
margin-bottom: 5px;
}
.topnav {
background-color: #000000;
overflow: hidden;
height: 47px;
}
.topnav a {
color: #f2f2f2;
text-align: center;
padding: 14px 16px;
text-decoration: none;
font-size: 17px;
}
.topnav a:hover {
background-color: #ddd;
color: black;
}
.topnav a.active {
background-color: #281c1c;
color: white;
}
.topnav .icon {
display: none;
}
@media screen and (max-width: 1049px) {
.topnav a:not(:first-child) {
display: none;
} }
.topnav a.icon { body {
float: right; font-family: Courier New;
display: block; text-align: center;
align-items: center;
font-size: xx-large;
font-weight: 700;
} }
}
@media screen and (max-width: 1049px) { .wrapper {
.topnav.responsive { min-height: calc(100vh - 50px);
position: relative; }
height: 247px;
.footer {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 600;
height: 50px;
color: #e7e7e7;
}
.footer > a {
font-family: Courier New;
text-align: center;
font-size: large;
font-weight: 700;
margin: 0;
color: #e7e7e7;
text-decoration: none;
}
.sticky {
bottom: 0;
height: 50px;
}
textarea {
background-color: #281c1c;
color: azure;
border: dotted 2px #ce422b;
width: 670px;
height: 300px;
resize: none;
}
.title > p {
padding-left: 20px;
margin: 0;
padding-right: 20px;
color: #e7e7e7;
font-size: xx-large;
}
.title {
padding-top: 50px;
}
.separator {
border-top: solid #281c1c;
border-bottom: none;
border-left: none;
border-right: none;
margin-top: 40px;
width: clamp(700px, 70vw, 1200px);
}
.image-container {
margin-top: 40px;
min-height: 80px;
}
p {
font-size: medium;
}
.txtHead {
margin-bottom: 5px;
} }
.topnav { .topnav {
text-align: left; background-color: #000000;
height: 47px;
} }
.topnav.responsive a.icon { .topnav a {
position: absolute; color: #f2f2f2;
right: 0; text-align: center;
top: 0; padding: 14px 16px;
text-decoration: none;
font-size: 17px;
} }
.topnav.responsive a { .topnav a:hover {
float: none; background-color: #ddd;
display: block; color: black;
text-align: left;
} }
}
</style>
<div class="wrapper">
<div class="topnav" id="myTopnav">
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html">Rust for Arduboy</a>
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html">Image Converter</a>
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html" class="active">Tile
Converter</a>
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html">Sprite Converter</a>
<a href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html">.arduboy
Generator</a>
<a href="javascript:void(0);" class="icon" onclick="myFunction()">
<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="currentColor" class="bi bi-list"
viewBox="0 0 16 16">
<path fill-rule="evenodd"
d="M2.5 12a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5z" />
</svg>
</a>
</div>
<div class="title">
<p>Drop your tile sheet here</p>
</div>
<hr class="separator" />
<div class="image-container">
<div id="image-container"></div>
</div>
<hr class="separator" />
</div>
<footer class="footer"> .topnav a.active {
<a href="https://github.com/ZennDev1337/" target="_blank">By ZennDev1337</a> background-color: #281c1c;
</footer> color: white;
<script language="JavaScript">
function myFunction() {
var x = document.getElementById("myTopnav");
if (x.className === "topnav") {
x.className += " responsive";
} else {
x.className = "topnav";
} }
}
</script> .topnav .icon {
<script language="JavaScript"> display: none;
function swapImage(t, e) { }
var r = t.getAttribute("data-srcnm");
t.removeAttribute("srcset"), @media screen and (max-width: 800px) {
r || t.setAttribute("data-srcnm", t.src), .topnav a:not(:first-child) {
(t.src = e); display: none;
} }
function setOriginal(t) {
var e = "", .topnav a.icon {
r = ""; float: right;
(r = t.getAttribute("data-srcmd")), display: block;
(e = t.getAttribute("data-srcnm")), }
r }
? ((t.src = r), t.removeAttribute("data-srcmd"))
: ((t.src = e), t.removeAttribute("data-srcnm")); @media screen and (max-width: 800px) {
} .topnav.responsive {
function swapImageMD(t, e) { position: relative;
t.setAttribute("data-srcmd", t.src), (t.src = e); height: auto;
} }
function jsready(t) {
/in/.test(document.readyState) .topnav {
? setTimeout("jsready(" + t + ")", 9) text-align: left;
: t(); }
}
jsready(function () { .topnav.responsive a.icon {
var t = window.devicePixelRatio ? window.devicePixelRatio : 1; position: absolute;
if (t > 1) right: 0;
for ( top: 0;
var e = document.getElementsByTagName("img"), r = 0; }
r < e.length;
r++ .topnav.responsive a {
) float: none;
e[r].getAttribute("data-src2x") && display: block;
(e[r].setAttribute( text-align: left;
"data-src-orig", }
e[r].getAttribute("src") }
), </style>
<div class="wrapper">
<div class="topnav" id="myTopnav">
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/index.html"
><nobr>Rust for Arduboy</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/image-converter.html"
><nobr>Image Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/tile-converter.html"
class="active"
><nobr>Tile Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/sprite-converter.html"
><nobr>Sprite Converter</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/arduboy-file-converter.html"
><nobr>.arduboy Generator</nobr></a
>
<a
href="https://zenndev1337.github.io/Rust-for-Arduboy/fxdata-converter.html"
><nobr>fxdata.h Converter</nobr></a
>
<a
href="javascript:void(0);"
class="icon"
onclick="myFunction()"
>
<svg
xmlns="http://www.w3.org/2000/svg"
width="16"
height="16"
fill="currentColor"
class="bi bi-list"
viewBox="0 0 16 16"
>
<path
fill-rule="evenodd"
d="M2.5 12a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5zm0-4a.5.5 0 0 1 .5-.5h10a.5.5 0 0 1 0 1H3a.5.5 0 0 1-.5-.5z"
/>
</svg>
</a>
</div>
<div class="title">
<p>Drop your tile sheet here</p>
</div>
<hr class="separator" />
<div class="image-container">
<div id="image-container"></div>
</div>
<hr class="separator" />
</div>
<footer class="footer">
<a href="https://github.com/ZennDev1337/" target="_blank"
>By ZennDev1337</a
>
</footer>
<script language="JavaScript">
function myFunction() {
var x = document.getElementById("myTopnav");
if (x.className === "topnav") {
x.className += " responsive";
} else {
x.className = "topnav";
}
}
</script>
<script language="JavaScript">
function swapImage(t, e) {
var r = t.getAttribute("data-srcnm");
t.removeAttribute("srcset"),
r || t.setAttribute("data-srcnm", t.src),
(t.src = e);
}
function setOriginal(t) {
var e = "",
r = "";
(r = t.getAttribute("data-srcmd")),
(e = t.getAttribute("data-srcnm")),
r
? ((t.src = r), t.removeAttribute("data-srcmd"))
: ((t.src = e), t.removeAttribute("data-srcnm"));
}
function swapImageMD(t, e) {
t.setAttribute("data-srcmd", t.src), (t.src = e);
}
function jsready(t) {
/in/.test(document.readyState)
? setTimeout("jsready(" + t + ")", 9)
: t();
}
jsready(function () {
var t = window.devicePixelRatio ? window.devicePixelRatio : 1;
if (t > 1)
for (
var e = document.getElementsByTagName("img"), r = 0;
r < e.length;
r++
)
e[r].getAttribute("data-src2x") &&
(e[r].setAttribute(
"data-src-orig",
e[r].getAttribute("src")
),
e[r].setAttribute( e[r].setAttribute(
"src", "src",
e[r].getAttribute("data-src2x") e[r].getAttribute("data-src2x")
)); ));
}); });
function setup(body) { function setup(body) {
body.ondragover = function () { body.ondragover = function () {
return false; return false;
}; };
body.ondragend = function () { body.ondragend = function () {
return false; return false;
}; };
body.ondrop = function (e) { body.ondrop = function (e) {
// Prevent the browser from showing the dropped file // Prevent the browser from showing the dropped file
e.preventDefault(); e.preventDefault();
// Get the image data // Get the image data
var imageData = getImageData(e); var imageData = getImageData(e);
// If there is some data, add it to the page // If there is some data, add it to the page
if (imageData !== null) { if (imageData !== null) {
addDroppedElement(imageData); addDroppedElement(imageData);
} }
}; };
}
function getImageData(event) {
var file = event.dataTransfer.files[0];
if (file.type.indexOf("image") === 0) {
return file;
} }
} function getImageData(event) {
function addDroppedElement(imageData) { var file = event.dataTransfer.files[0];
var reader = new FileReader(); if (file.type.indexOf("image") === 0) {
reader.onload = function (event) { return file;
event.preventDefault; }
// Create image element }
var droppedImage = new Image(); function addDroppedElement(imageData) {
droppedImage.src = event.target.result; var reader = new FileReader();
// add delay so the image can be loaded properly before accessing it reader.onload = function (event) {
setTimeout(function () { event.preventDefault;
var imgNW = droppedImage.naturalWidth; // Create image element
var imgNH = droppedImage.naturalHeight; var droppedImage = new Image();
var zoom = 1; droppedImage.src = event.target.result;
switch (imgNW) { // add delay so the image can be loaded properly before accessing it
case 8: setTimeout(function () {
zoom = 4; var imgNW = droppedImage.naturalWidth;
break; var imgNH = droppedImage.naturalHeight;
case 16: var zoom = 1;
zoom = 2; switch (imgNW) {
break; case 8:
case 24: zoom = 4;
zoom = 4 / 3; break;
break; case 16:
case 24: zoom = 2;
zoom = 1; break;
break; case 24:
} zoom = 4 / 3;
var tileW = imgNW * zoom; break;
var tileH = tileW; case 24:
// Create canvas for tiles zoom = 1;
var droppedImageCanvas = break;
document.createElement("canvas");
var canvasWidth =
Math.floor(700 / (tileW + 2)) * (tileW + 2) - 2;
var canvasHeight =
Math.ceil(
imgNH / imgNW / Math.floor(700 / (tileW + 2))
) *
(tileH + 2) -
2;
droppedImageCanvas.width = canvasWidth;
droppedImageCanvas.height = canvasHeight;
// Create invisible canvas for original image
var invisImageCanvas = document.createElement("canvas");
invisImageCanvas.width = imgNW;
invisImageCanvas.height = imgNH;
invisImageCanvas.style.display = "none";
// Create code container
var droppedImageCode =
document.createElement("textarea");
droppedImageCode.className = "code";
droppedImageCode.style.width = "698px";
droppedImageCode.rows = "20";
// Create div container
var droppedImageDiv = document.createElement("div");
droppedImageDiv.className = "image-view";
droppedImageDiv.appendChild(droppedImageCanvas);
droppedImageDiv.appendChild(invisImageCanvas);
var imageContainer =
document.getElementById("image-container");
imageContainer.innerHTML = "";
imageContainer.appendChild(droppedImageDiv);
imageContainer.appendChild(
document.createElement("br")
);
imageContainer.appendChild(droppedImageCode);
// Create context for drawing
var droppedImageContext =
droppedImageCanvas.getContext("2d");
droppedImageContext.imageSmoothingEnabled = false;
var invisImageContext =
invisImageCanvas.getContext("2d");
// Draw the image on an invisible canvas to generate the code
invisImageContext.drawImage(droppedImage, 0, 0);
// Clip the image and draw individual tiles on the canvas with 2px spacing inbetween
for (
var i = 0, x = 0, y = 0, tile;
i < imgNH / imgNW;
i++
) {
if (x + tileW + 2 <= canvasWidth) {
x += tileW + 2;
} else {
x = 0;
y += tileH + 2;
} }
if (i === 0) { var tileW = imgNW * zoom;
x = 0; var tileH = tileW;
} // Create canvas for tiles
droppedImageContext.drawImage( var droppedImageCanvas =
droppedImage, document.createElement("canvas");
0, var canvasWidth =
i * imgNW, Math.floor(700 / (tileW + 2)) * (tileW + 2) - 2;
imgNW, var canvasHeight =
imgNW, Math.ceil(
x, imgNH / imgNW / Math.floor(700 / (tileW + 2))
y, ) *
tileW, (tileH + 2) -
tileH 2;
droppedImageCanvas.width = canvasWidth;
droppedImageCanvas.height = canvasHeight;
// Create invisible canvas for original image
var invisImageCanvas = document.createElement("canvas");
invisImageCanvas.width = imgNW;
invisImageCanvas.height = imgNH;
invisImageCanvas.style.display = "none";
// Create code container
var droppedImageCode =
document.createElement("textarea");
droppedImageCode.className = "code";
droppedImageCode.style.width = "698px";
droppedImageCode.rows = "20";
// Create div container
var droppedImageDiv = document.createElement("div");
droppedImageDiv.className = "image-view";
droppedImageDiv.appendChild(droppedImageCanvas);
droppedImageDiv.appendChild(invisImageCanvas);
var imageContainer =
document.getElementById("image-container");
imageContainer.innerHTML = "";
imageContainer.appendChild(droppedImageDiv);
imageContainer.appendChild(
document.createElement("br")
); );
} imageContainer.appendChild(droppedImageCode);
// Draw raster between tiles on the canvas // Create context for drawing
droppedImageContext.beginPath(); var droppedImageContext =
for ( droppedImageCanvas.getContext("2d");
var j = 1; droppedImageContext.imageSmoothingEnabled = false;
j <= Math.floor(700 / (tileW + 2)); var invisImageContext =
j++ invisImageCanvas.getContext("2d");
) { // Draw the image on an invisible canvas to generate the code
droppedImageContext.moveTo( invisImageContext.drawImage(droppedImage, 0, 0);
j * tileW + 1 + (j - 1) * 2, // Clip the image and draw individual tiles on the canvas with 2px spacing inbetween
0
);
droppedImageContext.lineTo(
j * tileW + 1 + (j - 1) * 2,
canvasHeight
);
}
for (
var k = 1;
k <=
Math.ceil(
imgNH / imgNW / Math.floor(700 / tileW + 2)
);
k++
) {
droppedImageContext.moveTo(
0,
k * tileW + 1 + (k - 1) * 2
);
droppedImageContext.lineTo(
canvasWidth,
k * tileW + 1 + (k - 1) * 2
);
}
droppedImageContext.strokeStyle = "#281c1c";
droppedImageContext.lineWidth = 2;
droppedImageContext.stroke();
let sep =
window.document.getElementsByClassName("separator");
for (let item of sep) {
item.style.borderColor = "#ce422b";
}
// Generate the sprite string
var spriteString =
"static " +
imageData.name.split("_")[0] +
": [u8;_] = " +
"[\n" +
imgNW +
", " +
imgNW +
", // width, height,\n" +
"// TILE 00\n";
var pageCount = Math.ceil(imgNH / 8);
var columnCount = imgNW;
var currentByte = 0;
var rowCounter = 0;
var tileCounter = 0;
// Read the sprite page-by-page
for (var page = 0; page < pageCount; page++) {
// Read the page column-by-column
for ( for (
var column = 0; var i = 0, x = 0, y = 0, tile;
column < columnCount; i < imgNH / imgNW;
column++ i++
) { ) {
// Read the column into a byte if (x + tileW + 2 <= canvasWidth) {
var spriteByte = 0; x += tileW + 2;
for (var yPixel = 0; yPixel < 8; yPixel++) { } else {
// If the color of the pixel is not black, count it as white x = 0;
var pixelColor = y += tileH + 2;
invisImageContext.getImageData(
column,
page * 8 + yPixel,
1,
1
).data;
if (
pixelColor[0] > 0 ||
pixelColor[1] > 0 ||
pixelColor[2] > 0
) {
spriteByte |= 1 << yPixel;
}
} }
// Print the column in hex notation, add a comma for formatting if (i === 0) {
var digitStr = spriteByte.toString(16); x = 0;
if (digitStr.length == 1) {
digitStr = "0" + digitStr;
} }
spriteString += "0x" + digitStr + ", "; droppedImageContext.drawImage(
if (currentByte % imgNW == imgNW - 1) { droppedImage,
spriteString += "\n"; 0,
rowCounter++; i * imgNW,
if ( imgNW,
rowCounter == imgNW / 8 && imgNW,
tileCounter < imgNH / imgNW - 1 x,
) { y,
tileCounter++; tileW,
var tileNumber = tileH
tileCounter.toString().length === 1 );
? "0" + tileCounter.toString()
: tileCounter.toString();
spriteString +=
"// TILE " + tileNumber + "\n";
rowCounter = 0;
}
}
currentByte++;
} }
} // Draw raster between tiles on the canvas
// Terminate the array droppedImageContext.beginPath();
spriteString += "];"; for (
// Create an invisible element containing the string var j = 1;
droppedImageCode.innerHTML = spriteString; j <= Math.floor(700 / (tileW + 2));
}, 50); j++
}; ) {
reader.readAsDataURL(imageData); droppedImageContext.moveTo(
} j * tileW + 1 + (j - 1) * 2,
</script> 0
</body> );
droppedImageContext.lineTo(
</html> j * tileW + 1 + (j - 1) * 2,
canvasHeight
);
}
for (
var k = 1;
k <=
Math.ceil(
imgNH / imgNW / Math.floor(700 / tileW + 2)
);
k++
) {
droppedImageContext.moveTo(
0,
k * tileW + 1 + (k - 1) * 2
);
droppedImageContext.lineTo(
canvasWidth,
k * tileW + 1 + (k - 1) * 2
);
}
droppedImageContext.strokeStyle = "#281c1c";
droppedImageContext.lineWidth = 2;
droppedImageContext.stroke();
let sep =
window.document.getElementsByClassName("separator");
for (let item of sep) {
item.style.borderColor = "#ce422b";
}
// Generate the sprite string
var spriteString =
"static " +
imageData.name.split("_")[0] +
": [u8;_] = " +
"[\n" +
imgNW +
", " +
imgNW +
", // width, height,\n" +
"// TILE 00\n";
var pageCount = Math.ceil(imgNH / 8);
var columnCount = imgNW;
var currentByte = 0;
var rowCounter = 0;
var tileCounter = 0;
// Read the sprite page-by-page
for (var page = 0; page < pageCount; page++) {
// Read the page column-by-column
for (
var column = 0;
column < columnCount;
column++
) {
// Read the column into a byte
var spriteByte = 0;
for (var yPixel = 0; yPixel < 8; yPixel++) {
// If the color of the pixel is not black, count it as white
var pixelColor =
invisImageContext.getImageData(
column,
page * 8 + yPixel,
1,
1
).data;
if (
pixelColor[0] > 0 ||
pixelColor[1] > 0 ||
pixelColor[2] > 0
) {
spriteByte |= 1 << yPixel;
}
}
// Print the column in hex notation, add a comma for formatting
var digitStr = spriteByte.toString(16);
if (digitStr.length == 1) {
digitStr = "0" + digitStr;
}
spriteString += "0x" + digitStr + ", ";
if (currentByte % imgNW == imgNW - 1) {
spriteString += "\n";
rowCounter++;
if (
rowCounter == imgNW / 8 &&
tileCounter < imgNH / imgNW - 1
) {
tileCounter++;
var tileNumber =
tileCounter.toString().length === 1
? "0" + tileCounter.toString()
: tileCounter.toString();
spriteString +=
"// TILE " + tileNumber + "\n";
rowCounter = 0;
}
}
currentByte++;
}
}
// Terminate the array
spriteString += "];";
// Create an invisible element containing the string
droppedImageCode.innerHTML = spriteString;
}, 50);
};
reader.readAsDataURL(imageData);
}
</script>
</body>
</html>