Files
robo_public/karel/scripts/obecne-funkce.js
T
vojta@alfred 4e5c55e846 Prvni commit.
2026-02-01 00:00:07 +01:00

496 lines
12 KiB
JavaScript

/*
* [Česky]
* Projekt: Robot Karel
* Copyright: Viz KOPIROVANI v kořenovém adresáři projektu
*
* [English]
* Project: Karel, the Robot
* Copyright: See COPYING in the top level directory
*/
// JavaScript - různé funkce
// ===========================================================================
// =~ Globální proměnné ~=====================================================
je_oldium_dot_home = false;
if ( /^https?:\/\/[^\/]+\.oldium\.home\//.exec(document.URL) ) {
je_oldium_dot_home = true;
}
// ===========================================================================
// =~ Chyba při provádění příkazů ~===========================================
Chyba = function (chyba, text)
{
if ( chyba != undefined ) {
if ( chyba instanceof Chyba ) {
this.chyba = chyba.chyba;
this.text = chyba.formatuj( chyba.text );
this.zobrazen = chyba.zobrazen;
} else {
this.chyba = chyba;
this.text = text;
this.zobrazen = false;
}
} else {
this.chyba = false;
this.zobrazen = false;
}
}
Chyba.prototype.nastav = function (chyba, text)
{
if ( !this.chyba ) {
if ( chyba instanceof Chyba ) {
this.chyba = chyba.chyba;
this.text = chyba.formatuj(chyba.text);
this.zobrazen = this.zobrazen || chyba.zobrazen;
} else {
this.chyba = chyba;
this.text = text;
}
}
}
Chyba.prototype.formatuj = function (text)
{
return text;
}
Chyba.prototype.zobraz = function ()
{
if ( !this.zobrazen && this.chyba && this.text ) {
alert( this.formatuj(this.text) );
this.zobrazen = true;
}
}
Chyba.prototype.byla_chyba = function ()
{
return this.chyba;
}
// ===========================================================================
// =~ Výsledek provedení příkazu ~============================================
Vysledek = function (chyba, stav, hodnota)
{
if ( !chyba ) chyba = new Chyba();
this.chyba = chyba; // Chyba
this.stav = stav;
this.hodnota = hodnota; // Hodnota výsledku
}
Vysledek.NIC = 0; // Žádná zvláštní akce
Vysledek.PROVEDL_AKCI = 1; // Pokud byl proveden KROK, VLEVO-VBOK atp.
Vysledek.PRESKOC_KONEC = 2; // Pokud se má přeskočit blok příkazů
Vysledek.KONEC = 4; // Okamžitý konec
Vysledek.BYL_UPRAVEN = 8; // Příkaz byl upraven
Vysledek.MASKA = Vysledek.KONEC|Vysledek.BYL_UPRAVEN; // Maska neměnnosti
Vysledek.prototype.nastav = function (chyba, stav, hodnota)
{
if ( chyba != null ) {
if ( chyba instanceof Vysledek ) {
var vysledek = chyba;
if ( ! this.chyba.byla_chyba() ) {
this.chyba.nastav( vysledek.chyba );
this.stav =
(this.stav & Vysledek.MASKA) | (vysledek.stav & (~Vysledek.MASKA));
this.hodnota = vysledek.hodnota;
}
this.stav |= vysledek.stav&Vysledek.MASKA;
} else {
this.chyba.nastav( chyba );
this.stav =
((this.stav | stav) & Vysledek.MASKA) | (stav & (~Vysledek.MASKA));
this.hodnota = hodnota;
}
}
}
Vysledek.prototype.byla_chyba = function ()
{
return this.chyba.byla_chyba();
}
Vysledek.prototype.byla_akce = function ()
{
return this.stav & Vysledek.PROVEDL_AKCI;
}
Vysledek.prototype.byl_upraven = function ()
{
return this.stav & Vysledek.BYL_UPRAVEN;
}
Vysledek.prototype.je_konec = function ()
{
return this.chyba.byla_chyba() || (this.stav & Vysledek.KONEC);
}
Vysledek.prototype.je_hodnota = function ()
{
return ( !this.chyba.byla_chyba()
&& this.hodnota != undefined && this.hodnota != null );
}
Vysledek.prototype.ma_preskocit = function ()
{
return this.stav & Vysledek.PRESKOC_KONEC;
}
Vysledek.prototype.zobraz_chybu = function ()
{
this.chyba.zobraz();
}
// ===========================================================================
// =~ Příkazy po nahrání dokumentu ~==========================================
seznam_po_spusteni = new Array();
function po_spusteni (funkce) {
seznam_po_spusteni.push(funkce);
}
function spust_po_spusteni () {
for ( var i = 0; i < seznam_po_spusteni.length; i++ ) {
var funkce = seznam_po_spusteni[i];
funkce();
}
}
// ===========================================================================
// =~ Nahrání nápovědy a příkladů ~===========================================
okno_napoveda = null;
okno_priklady = null;
function otevri_okno( url, jmeno, okno )
{
try {
if ( okno && okno.closed() ) {
okno = null;
}
} catch (e) {
okno = null;
}
if ( !okno ) {
okno = window.open( url, jmeno );
}
if ( okno ) {
okno.focus();
}
return okno;
}
function napoveda() {
okno_napoveda = otevri_okno(
"napoveda.html", "karel_napoveda", okno_napoveda
);
}
function priklady() {
okno_priklady = otevri_okno(
"priklady.html", "karel_okno", okno_priklady
);
}
// ===========================================================================
// =~ Různé funkce ~==========================================================
// Test shodnosti dvou objektů
function jsou_shodne(a, b)
{
if ( a == null || b == null ) return false;
var type_a = typeof(a);
var type_b = typeof(b);
if ( type_a != type_b ) return false;
if ( type_a == "object" ) {
var pocet=0;
for ( var x in a ) {
if ( a[x] != b[x] ) {
return false;
}
pocet++;
}
for ( var x in b ) {
pocet--;
}
return (pocet == 0);
} else {
return (a == b);
}
}
// Vrať textovou reprezentaci
function formatuj_text(text)
{
if ( text == undefined ) {
return "nedefinován";
} else if ( text == null ) {
return "prázdný";
} else {
switch ( typeof(text) ) {
case "boolean":
if ( text ) {
return "ano";
} else {
return "ne";
}
case "object":
if ( text instanceof Date ) {
var format = text.getUTCFullYear() + "-" +
new String("0"+(text.getMonth()+1)).slice(-2) + "-" +
new String("0"+(text.getDate())).slice(-2) + " " +
new String("0"+(text.getHours())).slice(-2) + ":" +
new String("0"+(text.getMinutes())).slice(-2) + ":" +
new String("0"+(text.getSeconds())).slice(-2) + "." +
new String("00"+(text.getMilliseconds())).slice(-3);
return format;
} else if ( "innerText" in text || "innerHTML" in text
|| typeof(Element) == "object" && text instanceof Element ) {
var navrat = "";
for ( var hodnota in text ) {
var neni_text = ! /^((inner|outer)(HTML|Text)|text(Content)?)$/.exec(hodnota);
var neni_funkce = (typeof(text[hodnota]) != "function");
if ( neni_text && neni_funkce ) {
navrat += hodnota+":"+text[hodnota]+" ";
}
}
return navrat.slice(0,-1);
} else {
var hodnoty = new Array();
var navrat = "";
for ( var hodnota in text ) {
var neni_funkce = (typeof(text[hodnota]) != "function");
if ( neni_funkce ) {
hodnoty.push(hodnota);
navrat += hodnota+":"+text[hodnota]+" ";
}
}
if ( hodnoty.length == 2 &&
hodnoty[0] == 'x' || hodnoty[0] == 'y' &&
hodnoty[1] == 'x' || hodnoty[1] == 'y'
) {
return "x:"+(text.x+1)+" y:"+(text.y+1);
} else {
return navrat.slice(0,-1);
}
}
default:
return ""+text;
}
}
}
// Nastav hodnotu cookie. Lze zadat buď čas, nebo počet dnů do vypršení
function nastav_cookie(nazev, hodnota, vyprsi)
{
var text_vyprsi = "";
if ( vyprsi != undefined ) {
var datum;
if ( typeof(vyprsi) == "object" ) {
datum = text_vyprsi;
} else {
datum = new Date();
datum.setTime(datum.getTime()+(vyprsi*24*60*60*1000));
}
text_vyprsi = "; expires="+datum.toUTCString();
}
var uloz = escape(hodnota);
ladici_vypis(LADENI, "pridej_cookie", "nastavuji cookie "+nazev+"="+hodnota);
document.cookie = nazev+"="+uloz+text_vyprsi+"; path=/";
}
// Zjisti hodnotu cookie
function hodnota_cookie(nazev)
{
var vyhledej = nazev + "=";
var cookie = document.cookie.split(";");
for ( var i = 0; i < cookie.length; i++ ) {
var hodnota = cookie[i];
while ( hodnota.charAt(0) == " " ) {
hodnota = hodnota.slice(1);
}
if ( hodnota.indexOf(vyhledej) == 0 ) {
var vrat = unescape(hodnota.slice(vyhledej.length));
ladici_vypis(LADENI, "hodnota_cookie", "hodnota cookie "+nazev+"="+vrat);
return vrat;
}
}
ladici_vypis(LADENI, "hodnota_cookie", "hodnota cookie "+nazev+" nenalezena");
return null;
}
// Zruš cookie
function zrus_cookie(nazev)
{
pridej_cookie(nazev, "", -1);
}
// Nastav text objektu
function nastav_text(element, text)
{
if ( (element.firstChild &&
(( typeof(Text) != "undefined" && element.firstChild instanceof Text ) ||
element.firstChild.splitText
))
) {
if ( text == "" ) {
element.removeChild(element.firstChild);
} else {
element.firstChild.nodeValue = text;
}
} else {
if ( text != "" ) {
element.insertBefore(document.createTextNode(text), element.firstChild);
}
}
}
// Zjisti zdrojový element události (např. kde bylo kliknuto)
function zdrojovy_element(udalost)
{
if ( ! udalost ) {
return undefined;
} else if ( udalost.currentTarget ) {
return udalost.currentTarget;
} else if ( udalost.srcElement ) {
return udalost.srcElement;
} else {
return undefined;
}
}
// Zjisti pozici objektu
function zjisti_pozici(objekt)
{
if ( objekt != null ) {
var otec = zjisti_pozici(objekt.offsetParent);
return {
x: objekt.offsetLeft+otec.x,
y: objekt.offsetTop+otec.y
};
} else {
return { x: 0, y: 0 };
}
}
// Zjisti velikost objektu
function zjisti_velikost(objekt)
{
return { x: objekt.clientWidth, y: objekt.clientHeight };
}
// Zjisti velikost okna prohlížeče - pouze viditelnou část bez posuvníků
function zjisti_velikost_okna()
{
var velikost1 = zjisti_pozici( document.getElementById('okno1') );
var velikost2 = zjisti_velikost( document.getElementById('okno2') );
if ( velikost1.x != 0 || velikost1.y != 0 || velikost2.x == 0 ) {
return velikost1;
} else {
return velikost2;
}
}
// Zjisti pozici posuvníků
function zjisti_scroll()
{
var element = document.documentElement;
var body = document.body;
return {
x: Math.max(body.scrollLeft, element.scrollLeft),
y: Math.max(body.scrollTop, element.scrollTop)
};
}
// Spočítej rozměry (okraje) podle pozice a velikost
function spocitej_rozmery(pozice, velikost)
{
return {
levy: pozice.x,
pravy: pozice.x + velikost.x,
horni: pozice.y,
dolni: pozice.y + velikost.y
};
}
// Zmenši okraj o dané rozměry
function pridej_okraj(rozmery, okraj)
{
return {
levy: rozmery.levy + okraj,
horni: rozmery.horni + okraj,
pravy: rozmery.pravy - okraj,
dolni: rozmery.dolni - okraj
}
}
// Posun horizontálně
function posun_x(rozmery, posun)
{
return {
levy: rozmery.levy + posun,
horni: rozmery.horni,
pravy: rozmery.pravy + posun,
dolni: rozmery.dolni
};
}
// Posun vertikálně
function posun_y(rozmery, posun)
{
return {
levy: rozmery.levy,
horni: rozmery.horni + posun,
pravy: rozmery.pravy,
dolni: rozmery.dolni + posun
};
}
// Zjisti rozměry objektu. Pokud není určen objekt, vrať velikost okna
// prohlížeče a stránky
function zjisti_rozmery(objekt)
{
if ( objekt != undefined ) {
return spocitej_rozmery(zjisti_pozici(objekt), zjisti_velikost(objekt));
} else {
var okraj = document.getElementById('okraj').offsetTop/2;
var stranka = document.getElementById('stranka');
var velikost_okna = zjisti_velikost_okna();
var scroll = zjisti_scroll();
var okno_rozmery = {
levy: scroll.x,
horni: scroll.y,
pravy: scroll.x + velikost_okna.x,
dolni: scroll.y + velikost_okna.y
};
// Rozměry stránky nemůžou být menší, než je okno prohlížeče
var stranka_rozmery = {
levy: 0,
horni: 0,
pravy: Math.max( stranka.offsetWidth, okno_rozmery.pravy ),
dolni: Math.max( stranka.offsetHeight, okno_rozmery.dolni )
};
ladici_vypis(LADENI, "zjisti_rozmery", okno_rozmery, "rozměry okna");
ladici_vypis(LADENI, "zjisti_rozmery", stranka_rozmery, "rozměry stránky");
return {
okno: pridej_okraj( okno_rozmery, okraj ),
stranka: pridej_okraj( stranka_rozmery, okraj )
};
}
}