add precision client, remove starlike client, fix some css, update changelog
BIN
src/game/web/clients/precision/ProductSans.ttf
Normal file
1
src/game/web/clients/precision/arc-sw.js
Normal file
@ -0,0 +1 @@
|
|||||||
|
!function(t){var e={};function n(r){if(e[r])return e[r].exports;var o=e[r]={i:r,l:!1,exports:{}};return t[r].call(o.exports,o,o.exports,n),o.l=!0,o.exports}n.m=t,n.c=e,n.d=function(t,e,r){n.o(t,e)||Object.defineProperty(t,e,{enumerable:!0,get:r})},n.r=function(t){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(t,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(t,"__esModule",{value:!0})},n.t=function(t,e){if(1&e&&(t=n(t)),8&e)return t;if(4&e&&"object"==typeof t&&t&&t.__esModule)return t;var r=Object.create(null);if(n.r(r),Object.defineProperty(r,"default",{enumerable:!0,value:t}),2&e&&"string"!=typeof t)for(var o in t)n.d(r,o,function(e){return t[e]}.bind(null,o));return r},n.n=function(t){var e=t&&t.__esModule?function(){return t.default}:function(){return t};return n.d(e,"a",e),e},n.o=function(t,e){return Object.prototype.hasOwnProperty.call(t,e)},n.p="",n(n.s=93)}({3:function(t,e,n){"use strict";n.d(e,"a",(function(){return r})),n.d(e,"c",(function(){return o})),n.d(e,"g",(function(){return i})),n.d(e,"j",(function(){return a})),n.d(e,"i",(function(){return d})),n.d(e,"b",(function(){return f})),n.d(e,"k",(function(){return u})),n.d(e,"d",(function(){return p})),n.d(e,"e",(function(){return l})),n.d(e,"f",(function(){return m})),n.d(e,"h",(function(){return v}));var r={images:["bmp","jpeg","jpg","ttf","pict","svg","webp","eps","svgz","gif","png","ico","tif","tiff","bpg","avif","jxl"],video:["mp4","3gp","webm","mkv","flv","f4v","f4p","f4bogv","drc","avi","mov","qt","wmv","amv","mpg","mp2","mpeg","mpe","m2v","m4v","3g2","gifv","mpv","av1","ts","tsv","tsa","m2t","m3u8"],audio:["mid","midi","aac","aiff","flac","m4a","m4p","mp3","ogg","oga","mogg","opus","ra","rm","wav","webm","f4a","pat"],interchange:["json","yaml","xml","csv","toml","ini","bson","asn1","ubj"],archives:["jar","iso","tar","tgz","tbz2","tlz","gz","bz2","xz","lz","z","7z","apk","dmg","rar","lzma","txz","zip","zipx"],documents:["pdf","ps","doc","docx","ppt","pptx","xls","otf","xlsx"],other:["srt","swf"]},o=["js","cjs","mjs","css"],c="arc:",i={COMLINK_INIT:"".concat(c,"comlink:init"),NODE_ID:"".concat(c,":nodeId"),CLIENT_TEARDOWN:"".concat(c,"client:teardown"),CLIENT_TAB_ID:"".concat(c,"client:tabId"),CDN_CONFIG:"".concat(c,"cdn:config"),P2P_CLIENT_READY:"".concat(c,"cdn:ready"),STORED_FIDS:"".concat(c,"cdn:storedFids"),SW_HEALTH_CHECK:"".concat(c,"cdn:healthCheck"),WIDGET_CONFIG:"".concat(c,"widget:config"),WIDGET_INIT:"".concat(c,"widget:init"),WIDGET_UI_LOAD:"".concat(c,"widget:load"),BROKER_LOAD:"".concat(c,"broker:load"),RENDER_FILE:"".concat(c,"inlay:renderFile"),FILE_RENDERED:"".concat(c,"inlay:fileRendered")},a="serviceWorker",d="/".concat("shared-worker",".js"),f="/".concat("dedicated-worker",".js"),u="/".concat("arc-sw-core",".js"),s="".concat("arc-sw",".js"),p=("/".concat(s),"/".concat("arc-sw"),"arc-db"),l="key-val-store",m=2**17,v="".concat("https://warden.arc.io","/mailbox/propertySession");"".concat("https://warden.arc.io","/mailbox/transfers")},93:function(t,e,n){"use strict";n.r(e);var r=n(3);if("undefined"!=typeof ServiceWorkerGlobalScope){var o="https://arc.io"+r.k;importScripts(o)}else if("undefined"!=typeof SharedWorkerGlobalScope){var c="https://arc.io"+r.i;importScripts(c)}else if("undefined"!=typeof DedicatedWorkerGlobalScope){var i="https://arc.io"+r.b;importScripts(i)}}});
|
54
src/game/web/clients/precision/assetoverrides/credits.txt
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
§fPrecision Client is a custom eaglercraft client with QOL §ffeatures, custom texture packs, and more.§r
|
||||||
|
|
||||||
|
§9This was created by LAX1DUDE and forked by EtcherFX§r
|
||||||
|
|
||||||
|
§4Ingame voice chat service created by ayunami2000§r
|
||||||
|
|
||||||
|
§2Click the Github or Discord button on the main menu for §2more information§r
|
||||||
|
|
||||||
|
§fScroll down for the detailed license statements
|
||||||
|
|
||||||
|
§fAll graphical assets in this project were ripped from §fMojang's official Minecraft.jar for Minecraft version §f1.5.2 §fand they are Mojang's intellectual property. Assets ommitted §finclude the Minecraft soundtrack and music disks and all §fsoftware references to the Mojang/Minecraft api.
|
||||||
|
|
||||||
|
§f========================================
|
||||||
|
|
||||||
|
§fCopyright (c) 2022 Calder Young.
|
||||||
|
|
||||||
|
§fThis work is licensed under a Creative Commons
|
||||||
|
§fAttribution-NonCommercial 4.0 International License
|
||||||
|
§f§nhttp://creativecommons.org/licenses/by-nc/4.0/§r
|
||||||
|
|
||||||
|
§f========================================
|
||||||
|
|
||||||
|
§fTeaVM Copyright 2016 Alexey Andreev.
|
||||||
|
|
||||||
|
§fLicensed under the Apache License, Version 2.0 (the §f"License"); you may not use this file except in compliance §fwith the License. You may obtain a copy of the License at
|
||||||
|
|
||||||
|
§f§nhttp://www.apache.org/licenses/LICENSE-2.0§r
|
||||||
|
|
||||||
|
§fUnless required by applicable law or agreed to in writing, §fsoftware distributed under the License is distributed on an §f"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY §fKIND, either express or implied. See the License for the §fspecific language governing permissions and limitations §funder the License.
|
||||||
|
|
||||||
|
§f========================================
|
||||||
|
|
||||||
|
§fNVIDIA FXAA 3.11 by TIMOTHY LOTTES
|
||||||
|
|
||||||
|
§fCopyright (c) 2010, 2011 NVIDIA CORPORATION. ALL RIGHTS §fRESERVED.
|
||||||
|
|
||||||
|
§fTO THE MAXIMUM EXTENT PERMITTED BY APPLICABLE LAW, §fTHIS SOFTWARE IS PROVIDED *AS IS* AND NVIDIA AND ITS §fSUPPLIERS DISCLAIM ALL WARRANTIES, EITHER EXPRESS OR §fIMPLIED, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES §fOF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. §fIN NO EVENT SHALL NVIDIA OR ITS SUPPLIERS BE LIABLE FOR §fANY SPECIAL, INCIDENTAL, INDIRECT, OR CONSEQUENTIAL §fDAMAGES WHATSOEVER (INCLUDING, WITHOUT LIMITATION, §fDAMAGES FOR LOSS OF BUSINESS PROFITS, BUSINESS §fINTERRUPTION, LOSS OF BUSINESS INFORMATION, OR ANY OTHER §fPECUNIARY LOSS) ARISING OUT OF THE USE OF OR INABILITY TO §fUSE THIS SOFTWARE, EVEN IF NVIDIA HAS BEEN ADVISED OF THE §fPOSSIBILITY OF SUCH DAMAGES.
|
||||||
|
|
||||||
|
§f========================================
|
||||||
|
|
||||||
|
§fJZlib Copyright (c) 2000-2011 ymnk, JCraft,Inc. All rights §freserved.
|
||||||
|
|
||||||
|
§fRedistribution and use in source and binary forms, with or §fwithout modification, are permitted provided that the following §fconditions are met:
|
||||||
|
|
||||||
|
§f1. Redistributions of source code must retain the above §fcopyright notice, this list of conditions and the following §fdisclaimer.
|
||||||
|
|
||||||
|
§f2. Redistributions in binary form must reproduce the §fabove copyright notice, this list of conditions and the §ffollowing disclaimer in the documentation and/or other §fmaterials provided with the distribution.
|
||||||
|
|
||||||
|
§f3. The names of the authors may not be used to endorse §for promote products derived from this software without §fspecific prior written permission.
|
||||||
|
|
||||||
|
§fTHIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESSED OR §fIMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE §fIMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A §fPARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL §fJCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE §fLIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, §fEXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT §fLIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; §fLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) §fHOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER §fIN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING §fNEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE §fUSE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY §fOF SUCH DAMAGE.
|
||||||
|
|
||||||
|
§f========================================
|
||||||
|
|
BIN
src/game/web/clients/precision/assetoverrides/gui/demo_bg.png
Normal file
After Width: | Height: | Size: 8.1 KiB |
1487
src/game/web/clients/precision/assetoverrides/lang/en_US.lang
Normal file
BIN
src/game/web/clients/precision/assetoverrides/precision/gui.png
Normal file
After Width: | Height: | Size: 11 KiB |
BIN
src/game/web/clients/precision/assetoverrides/precision/gui2.png
Normal file
After Width: | Height: | Size: 17 KiB |
After Width: | Height: | Size: 10 KiB |
BIN
src/game/web/clients/precision/assetoverrides/precision/logo.png
Normal file
After Width: | Height: | Size: 14 KiB |
After Width: | Height: | Size: 6.7 KiB |
After Width: | Height: | Size: 14 KiB |
After Width: | Height: | Size: 50 KiB |
After Width: | Height: | Size: 48 KiB |
After Width: | Height: | Size: 48 KiB |
After Width: | Height: | Size: 54 KiB |
After Width: | Height: | Size: 38 KiB |
After Width: | Height: | Size: 65 KiB |
BIN
src/game/web/clients/precision/bg.png
Normal file
After Width: | Height: | Size: 427 KiB |
19499
src/game/web/clients/precision/classes.js
Normal file
16300
src/game/web/clients/precision/classes_server.js
Normal file
798
src/game/web/clients/precision/eagswebrtc.js
Normal file
@ -0,0 +1,798 @@
|
|||||||
|
"use strict";
|
||||||
|
|
||||||
|
/*
|
||||||
|
|
||||||
|
This is the backend for voice channels and LAN servers in eaglercraft
|
||||||
|
|
||||||
|
it links with TeaVM EaglerAdapter at runtime
|
||||||
|
|
||||||
|
Copyright 2022 ayunami2000 & lax1dude. All rights reserved.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
// %%%%%%%%%%%%%%%%%%%%%%%%%%%%% VOICE CODE %%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
|
||||||
|
window.initializeVoiceClient = (() => {
|
||||||
|
|
||||||
|
const READYSTATE_NONE = 0;
|
||||||
|
const READYSTATE_ABORTED = -1;
|
||||||
|
const READYSTATE_DEVICE_INITIALIZED = 1;
|
||||||
|
|
||||||
|
const PEERSTATE_FAILED = 0;
|
||||||
|
const PEERSTATE_SUCCESS = 1;
|
||||||
|
const PEERSTATE_LOADING = 2;
|
||||||
|
|
||||||
|
class EaglercraftVoicePeer {
|
||||||
|
|
||||||
|
constructor(client, peerId, peerConnection, offer) {
|
||||||
|
this.client = client;
|
||||||
|
this.peerId = peerId;
|
||||||
|
this.peerConnection = peerConnection;
|
||||||
|
this.stream = null;
|
||||||
|
|
||||||
|
const self = this;
|
||||||
|
this.peerConnection.addEventListener("icecandidate", (evt) => {
|
||||||
|
if (evt.candidate) {
|
||||||
|
self.client.iceCandidateHandler(self.peerId, JSON.stringify({
|
||||||
|
sdpMLineIndex: evt.candidate.sdpMLineIndex,
|
||||||
|
candidate: evt.candidate.candidate
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
this.peerConnection.addEventListener("track", (evt) => {
|
||||||
|
self.rawStream = evt.streams[0];
|
||||||
|
const aud = new Audio();
|
||||||
|
aud.autoplay = true;
|
||||||
|
aud.muted = true;
|
||||||
|
aud.onended = function () {
|
||||||
|
aud.remove();
|
||||||
|
};
|
||||||
|
aud.srcObject = self.rawStream;
|
||||||
|
self.client.peerTrackHandler(self.peerId, self.rawStream);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.peerConnection.addStream(this.client.localMediaStream.stream);
|
||||||
|
if (offer) {
|
||||||
|
this.peerConnection.createOffer((desc) => {
|
||||||
|
const selfDesc = desc;
|
||||||
|
self.peerConnection.setLocalDescription(selfDesc, () => {
|
||||||
|
self.client.descriptionHandler(self.peerId, JSON.stringify(selfDesc));
|
||||||
|
if (self.client.peerStateInitial != PEERSTATE_SUCCESS) self.client.peerStateInitial = PEERSTATE_SUCCESS;
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to set local description for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateInitial == PEERSTATE_LOADING) self.client.peerStateInitial = PEERSTATE_FAILED;
|
||||||
|
self.client.signalDisconnect(self.peerId);
|
||||||
|
});
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to set create offer for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateInitial == PEERSTATE_LOADING) self.client.peerStateInitial = PEERSTATE_FAILED;
|
||||||
|
self.client.signalDisconnect(self.peerId);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
this.peerConnection.addEventListener("connectionstatechange", (evt) => {
|
||||||
|
if (self.peerConnection.connectionState === 'disconnected') {
|
||||||
|
self.client.signalDisconnect(self.peerId);
|
||||||
|
} else if (self.peerConnection.connectionState === 'connected') {
|
||||||
|
if (self.client.peerState != PEERSTATE_SUCCESS) self.client.peerState = PEERSTATE_SUCCESS;
|
||||||
|
} else if (self.peerConnection.connectionState === 'failed') {
|
||||||
|
if (self.client.peerState == PEERSTATE_LOADING) self.client.peerState = PEERSTATE_FAILED;
|
||||||
|
self.client.signalDisconnect(self.peerId);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
disconnect() {
|
||||||
|
this.peerConnection.close();
|
||||||
|
}
|
||||||
|
|
||||||
|
mute(muted) {
|
||||||
|
this.rawStream.getAudioTracks()[0].enabled = !muted;
|
||||||
|
}
|
||||||
|
|
||||||
|
setRemoteDescription(descJSON) {
|
||||||
|
const self = this;
|
||||||
|
try {
|
||||||
|
const remoteDesc = JSON.parse(descJSON);
|
||||||
|
this.peerConnection.setRemoteDescription(remoteDesc, () => {
|
||||||
|
if (remoteDesc.type == 'offer') {
|
||||||
|
self.peerConnection.createAnswer((desc) => {
|
||||||
|
const selfDesc = desc;
|
||||||
|
self.peerConnection.setLocalDescription(selfDesc, () => {
|
||||||
|
self.client.descriptionHandler(self.peerId, JSON.stringify(selfDesc));
|
||||||
|
if (self.client.peerStateDesc != PEERSTATE_SUCCESS) self.client.peerStateDesc = PEERSTATE_SUCCESS;
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to set local description for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateDesc == PEERSTATE_LOADING) self.client.peerStateDesc = PEERSTATE_FAILED;
|
||||||
|
self.client.signalDisconnect(self.peerId);
|
||||||
|
});
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to create answer for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateDesc == PEERSTATE_LOADING) self.client.peerStateDesc = PEERSTATE_FAILED;
|
||||||
|
self.client.signalDisconnect(self.peerId);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to set remote description for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateDesc == PEERSTATE_LOADING) self.client.peerStateDesc = PEERSTATE_FAILED;
|
||||||
|
self.client.signalDisconnect(self.peerId);
|
||||||
|
});
|
||||||
|
} catch (err) {
|
||||||
|
console.error("Failed to parse remote description for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateDesc == PEERSTATE_LOADING) self.client.peerStateDesc = PEERSTATE_FAILED;
|
||||||
|
self.client.signalDisconnect(self.peerId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
addICECandidate(candidate) {
|
||||||
|
try {
|
||||||
|
this.peerConnection.addIceCandidate(new RTCIceCandidate(JSON.parse(candidate)));
|
||||||
|
if (this.client.peerStateIce != PEERSTATE_SUCCESS) this.client.peerStateIce = PEERSTATE_SUCCESS;
|
||||||
|
} catch (err) {
|
||||||
|
console.error("Failed to parse ice candidate for \"" + this.peerId + "\"! " + err);
|
||||||
|
if (this.client.peerStateIce == PEERSTATE_LOADING) this.client.peerStateIce = PEERSTATE_FAILED;
|
||||||
|
this.client.signalDisconnect(this.peerId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class EaglercraftVoiceClient {
|
||||||
|
|
||||||
|
constructor() {
|
||||||
|
this.ICEServers = [];
|
||||||
|
this.hasInit = false;
|
||||||
|
this.peerList = new Map();
|
||||||
|
this.readyState = READYSTATE_NONE;
|
||||||
|
this.peerState = PEERSTATE_LOADING;
|
||||||
|
this.peerStateConnect = PEERSTATE_LOADING;
|
||||||
|
this.peerStateInitial = PEERSTATE_LOADING;
|
||||||
|
this.peerStateDesc = PEERSTATE_LOADING;
|
||||||
|
this.peerStateIce = PEERSTATE_LOADING;
|
||||||
|
this.iceCandidateHandler = null;
|
||||||
|
this.descriptionHandler = null;
|
||||||
|
this.peerTrackHandler = null;
|
||||||
|
this.peerDisconnectHandler = null;
|
||||||
|
this.microphoneVolumeAudioContext = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
voiceClientSupported() {
|
||||||
|
return typeof window.RTCPeerConnection !== "undefined" && typeof navigator.mediaDevices !== "undefined" &&
|
||||||
|
typeof navigator.mediaDevices.getUserMedia !== "undefined";
|
||||||
|
}
|
||||||
|
|
||||||
|
setICEServers(urls) {
|
||||||
|
this.ICEServers.length = 0;
|
||||||
|
for (var i = 0; i < urls.length; ++i) {
|
||||||
|
var etr = urls[i].split(";");
|
||||||
|
if (etr.length == 1) {
|
||||||
|
this.ICEServers.push({urls: etr[0]});
|
||||||
|
} else if (etr.length == 3) {
|
||||||
|
this.ICEServers.push({urls: etr[0], username: etr[1], credential: etr[2]});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setICECandidateHandler(cb) {
|
||||||
|
this.iceCandidateHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setDescriptionHandler(cb) {
|
||||||
|
this.descriptionHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setPeerTrackHandler(cb) {
|
||||||
|
this.peerTrackHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setPeerDisconnectHandler(cb) {
|
||||||
|
this.peerDisconnectHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
activateVoice(tk) {
|
||||||
|
if (this.hasInit) this.localRawMediaStream.getAudioTracks()[0].enabled = tk;
|
||||||
|
}
|
||||||
|
|
||||||
|
initializeDevices() {
|
||||||
|
if (!this.hasInit) {
|
||||||
|
const self = this;
|
||||||
|
navigator.mediaDevices.getUserMedia({audio: true, video: false}).then((stream) => {
|
||||||
|
self.microphoneVolumeAudioContext = new AudioContext();
|
||||||
|
self.localRawMediaStream = stream;
|
||||||
|
self.localRawMediaStream.getAudioTracks()[0].enabled = false;
|
||||||
|
self.localMediaStream = self.microphoneVolumeAudioContext.createMediaStreamDestination();
|
||||||
|
self.localMediaStreamGain = self.microphoneVolumeAudioContext.createGain();
|
||||||
|
var localStreamIn = self.microphoneVolumeAudioContext.createMediaStreamSource(stream);
|
||||||
|
localStreamIn.connect(self.localMediaStreamGain);
|
||||||
|
self.localMediaStreamGain.connect(self.localMediaStream);
|
||||||
|
self.localMediaStreamGain.gain.value = 1.0;
|
||||||
|
self.readyState = READYSTATE_DEVICE_INITIALIZED;
|
||||||
|
this.hasInit = true;
|
||||||
|
}).catch((err) => {
|
||||||
|
self.readyState = READYSTATE_ABORTED;
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
this.readyState = READYSTATE_DEVICE_INITIALIZED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setMicVolume(val) {
|
||||||
|
if (this.hasInit) {
|
||||||
|
if (val > 0.5) val = 0.5 + (val - 0.5) * 2.0;
|
||||||
|
if (val > 1.5) val = 1.5;
|
||||||
|
if (val < 0.0) val = 0.0;
|
||||||
|
this.localMediaStreamGain.gain.value = val * 2.0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
resetPeerStates() {
|
||||||
|
this.peerState = this.peerStateConnect = this.peerStateInitial = this.peerStateDesc = this.peerStateIce = PEERSTATE_LOADING;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerState() {
|
||||||
|
return this.peerState;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerStateConnect() {
|
||||||
|
return this.peerStateConnect;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerStateInitial() {
|
||||||
|
return this.peerStateInitial;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerStateDesc() {
|
||||||
|
return this.peerStateDesc;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerStateIce() {
|
||||||
|
return this.peerStateIce;
|
||||||
|
}
|
||||||
|
|
||||||
|
getReadyState() {
|
||||||
|
return this.readyState;
|
||||||
|
}
|
||||||
|
|
||||||
|
signalConnect(peerId, offer) {
|
||||||
|
if (!this.hasInit) this.initializeDevices();
|
||||||
|
try {
|
||||||
|
const peerConnection = new RTCPeerConnection({
|
||||||
|
iceServers: this.ICEServers,
|
||||||
|
optional: [{DtlsSrtpKeyAgreement: true}]
|
||||||
|
});
|
||||||
|
const peerInstance = new EaglercraftVoicePeer(this, peerId, peerConnection, offer);
|
||||||
|
this.peerList.set(peerId, peerInstance);
|
||||||
|
if (this.peerStateConnect != PEERSTATE_SUCCESS) this.peerStateConnect = PEERSTATE_SUCCESS;
|
||||||
|
} catch (e) {
|
||||||
|
if (this.peerStateConnect == PEERSTATE_LOADING) this.peerStateConnect = PEERSTATE_FAILED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalDescription(peerId, descJSON) {
|
||||||
|
var thePeer = this.peerList.get(peerId);
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
thePeer.setRemoteDescription(descJSON);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalDisconnect(peerId, quiet) {
|
||||||
|
var thePeer = this.peerList.get(peerId);
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
this.peerList.delete(thePeer);
|
||||||
|
try {
|
||||||
|
thePeer.disconnect();
|
||||||
|
} catch (e) {
|
||||||
|
}
|
||||||
|
this.peerDisconnectHandler(peerId, quiet);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
mutePeer(peerId, muted) {
|
||||||
|
var thePeer = this.peerList.get(peerId);
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
thePeer.mute(muted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalICECandidate(peerId, candidate) {
|
||||||
|
var thePeer = this.peerList.get(peerId);
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
thePeer.addICECandidate(candidate);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
window.constructVoiceClient = () => new EaglercraftVoiceClient();
|
||||||
|
});
|
||||||
|
|
||||||
|
window.startVoiceClient = () => {
|
||||||
|
if (typeof window.constructVoiceClient !== "function") {
|
||||||
|
window.initializeVoiceClient();
|
||||||
|
}
|
||||||
|
return window.constructVoiceClient();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// %%%%%%%%%%%%%%%%%%%%%%%%%%%%% LAN CLIENT CODE %%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
|
||||||
|
window.initializeLANClient = (() => {
|
||||||
|
|
||||||
|
const READYSTATE_INIT_FAILED = -2;
|
||||||
|
const READYSTATE_FAILED = -1;
|
||||||
|
const READYSTATE_DISCONNECTED = 0;
|
||||||
|
const READYSTATE_CONNECTING = 1;
|
||||||
|
const READYSTATE_CONNECTED = 2;
|
||||||
|
|
||||||
|
class EaglercraftLANClient {
|
||||||
|
|
||||||
|
constructor() {
|
||||||
|
this.ICEServers = [];
|
||||||
|
this.peerConnection = null;
|
||||||
|
this.dataChannel = null;
|
||||||
|
this.readyState = READYSTATE_CONNECTING;
|
||||||
|
this.iceCandidateHandler = null;
|
||||||
|
this.descriptionHandler = null;
|
||||||
|
this.remoteDataChannelHandler = null;
|
||||||
|
this.remoteDisconnectHandler = null;
|
||||||
|
this.remotePacketHandler = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
LANClientSupported() {
|
||||||
|
return typeof window.RTCPeerConnection !== "undefined";
|
||||||
|
}
|
||||||
|
|
||||||
|
initializeClient() {
|
||||||
|
try {
|
||||||
|
if (this.dataChannel != null) {
|
||||||
|
this.dataChannel.close();
|
||||||
|
this.dataChannel = null;
|
||||||
|
}
|
||||||
|
if (this.peerConnection != null) {
|
||||||
|
this.peerConnection.close();
|
||||||
|
}
|
||||||
|
this.peerConnection = new RTCPeerConnection({
|
||||||
|
iceServers: this.ICEServers,
|
||||||
|
optional: [{DtlsSrtpKeyAgreement: true}]
|
||||||
|
});
|
||||||
|
this.readyState = READYSTATE_CONNECTING;
|
||||||
|
} catch (e) {
|
||||||
|
this.readyState = READYSTATE_INIT_FAILED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setICEServers(urls) {
|
||||||
|
this.ICEServers.length = 0;
|
||||||
|
for (var i = 0; i < urls.length; ++i) {
|
||||||
|
var etr = urls[i].split(";");
|
||||||
|
if (etr.length == 1) {
|
||||||
|
this.ICEServers.push({urls: etr[0]});
|
||||||
|
} else if (etr.length == 3) {
|
||||||
|
this.ICEServers.push({urls: etr[0], username: etr[1], credential: etr[2]});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setICECandidateHandler(cb) {
|
||||||
|
this.iceCandidateHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setDescriptionHandler(cb) {
|
||||||
|
this.descriptionHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setRemoteDataChannelHandler(cb) {
|
||||||
|
this.remoteDataChannelHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setRemoteDisconnectHandler(cb) {
|
||||||
|
this.remoteDisconnectHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setRemotePacketHandler(cb) {
|
||||||
|
this.remotePacketHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
getReadyState() {
|
||||||
|
return this.readyState;
|
||||||
|
}
|
||||||
|
|
||||||
|
sendPacketToServer(buffer) {
|
||||||
|
if (this.dataChannel != null && this.dataChannel.readyState == "open") {
|
||||||
|
this.dataChannel.send(buffer);
|
||||||
|
} else {
|
||||||
|
this.signalRemoteDisconnect(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalRemoteConnect() {
|
||||||
|
const self = this;
|
||||||
|
|
||||||
|
const iceCandidates = [];
|
||||||
|
|
||||||
|
this.peerConnection.addEventListener("icecandidate", (evt) => {
|
||||||
|
if (evt.candidate) {
|
||||||
|
if (iceCandidates.length == 0) setTimeout(() => {
|
||||||
|
if (self.peerConnection != null && self.peerConnection.connectionState != "disconnected") {
|
||||||
|
self.iceCandidateHandler(JSON.stringify(iceCandidates));
|
||||||
|
iceCandidates.length = 0;
|
||||||
|
}
|
||||||
|
}, 3000);
|
||||||
|
iceCandidates.push({
|
||||||
|
sdpMLineIndex: evt.candidate.sdpMLineIndex,
|
||||||
|
candidate: evt.candidate.candidate
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
this.dataChannel = this.peerConnection.createDataChannel("lan");
|
||||||
|
this.dataChannel.binaryType = "arraybuffer";
|
||||||
|
|
||||||
|
this.dataChannel.addEventListener("open", async (evt) => {
|
||||||
|
while (iceCandidates.length > 0) {
|
||||||
|
await new Promise(resolve => setTimeout(resolve, 0));
|
||||||
|
}
|
||||||
|
self.remoteDataChannelHandler(self.dataChannel);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.dataChannel.addEventListener("message", (evt) => {
|
||||||
|
self.remotePacketHandler(evt.data);
|
||||||
|
}, false);
|
||||||
|
|
||||||
|
this.peerConnection.createOffer((desc) => {
|
||||||
|
const selfDesc = desc;
|
||||||
|
self.peerConnection.setLocalDescription(selfDesc, () => {
|
||||||
|
self.descriptionHandler(JSON.stringify(selfDesc));
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to set local description! " + err);
|
||||||
|
self.readyState = READYSTATE_FAILED;
|
||||||
|
self.signalRemoteDisconnect(false);
|
||||||
|
});
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to set create offer! " + err);
|
||||||
|
self.readyState = READYSTATE_FAILED;
|
||||||
|
self.signalRemoteDisconnect(false);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.peerConnection.addEventListener("connectionstatechange", (evt) => {
|
||||||
|
if (self.peerConnection.connectionState === 'disconnected') {
|
||||||
|
self.signalRemoteDisconnect(false);
|
||||||
|
} else if (self.peerConnection.connectionState === 'connected') {
|
||||||
|
self.readyState = READYSTATE_CONNECTED;
|
||||||
|
} else if (self.peerConnection.connectionState === 'failed') {
|
||||||
|
self.readyState = READYSTATE_FAILED;
|
||||||
|
self.signalRemoteDisconnect(false);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
signalRemoteDescription(descJSON) {
|
||||||
|
try {
|
||||||
|
this.peerConnection.setRemoteDescription(JSON.parse(descJSON));
|
||||||
|
} catch (e) {
|
||||||
|
console.error(e);
|
||||||
|
this.readyState = READYSTATE_FAILED;
|
||||||
|
this.signalRemoteDisconnect(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalRemoteICECandidate(candidates) {
|
||||||
|
try {
|
||||||
|
const candidateList = JSON.parse(candidates);
|
||||||
|
for (let candidate of candidateList) {
|
||||||
|
this.peerConnection.addIceCandidate(candidate);
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
console.error(e);
|
||||||
|
this.readyState = READYSTATE_FAILED;
|
||||||
|
this.signalRemoteDisconnect(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalRemoteDisconnect(quiet) {
|
||||||
|
if (this.dataChannel != null) {
|
||||||
|
this.dataChannel.close();
|
||||||
|
this.dataChannel = null;
|
||||||
|
}
|
||||||
|
if (this.peerConnection != null) {
|
||||||
|
this.peerConnection.close();
|
||||||
|
}
|
||||||
|
if (!quiet) this.remoteDisconnectHandler();
|
||||||
|
this.readyState = READYSTATE_DISCONNECTED;
|
||||||
|
}
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
window.constructLANClient = () => new EaglercraftLANClient();
|
||||||
|
});
|
||||||
|
|
||||||
|
window.startLANClient = () => {
|
||||||
|
if (typeof window.constructLANClient !== "function") {
|
||||||
|
window.initializeLANClient();
|
||||||
|
}
|
||||||
|
return window.constructLANClient();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// %%%%%%%%%%%%%%%%%%%%%%%%%%%%% LAN SERVER CODE %%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
|
||||||
|
window.initializeLANServer = (() => {
|
||||||
|
|
||||||
|
const PEERSTATE_FAILED = 0;
|
||||||
|
const PEERSTATE_SUCCESS = 1;
|
||||||
|
const PEERSTATE_LOADING = 2;
|
||||||
|
|
||||||
|
class EaglercraftLANPeer {
|
||||||
|
|
||||||
|
constructor(client, peerId, peerConnection) {
|
||||||
|
this.client = client;
|
||||||
|
this.peerId = peerId;
|
||||||
|
this.peerConnection = peerConnection;
|
||||||
|
this.dataChannel = null;
|
||||||
|
|
||||||
|
const self = this;
|
||||||
|
|
||||||
|
const iceCandidates = [];
|
||||||
|
|
||||||
|
this.peerConnection.addEventListener("icecandidate", (evt) => {
|
||||||
|
if (evt.candidate) {
|
||||||
|
if (iceCandidates.length == 0) setTimeout(() => {
|
||||||
|
if (self.peerConnection != null && self.peerConnection.connectionState != "disconnected") {
|
||||||
|
self.client.iceCandidateHandler(self.peerId, JSON.stringify(iceCandidates));
|
||||||
|
iceCandidates.length = 0;
|
||||||
|
}
|
||||||
|
}, 3000);
|
||||||
|
iceCandidates.push({
|
||||||
|
sdpMLineIndex: evt.candidate.sdpMLineIndex,
|
||||||
|
candidate: evt.candidate.candidate
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
this.peerConnection.addEventListener("datachannel", async (evt) => {
|
||||||
|
while (iceCandidates.length > 0) {
|
||||||
|
await new Promise(resolve => setTimeout(resolve, 0));
|
||||||
|
}
|
||||||
|
self.dataChannel = evt.channel;
|
||||||
|
self.client.remoteClientDataChannelHandler(self.peerId, self.dataChannel);
|
||||||
|
self.dataChannel.addEventListener("message", (evt) => {
|
||||||
|
self.client.remoteClientPacketHandler(self.peerId, evt.data);
|
||||||
|
}, false);
|
||||||
|
}, false);
|
||||||
|
|
||||||
|
this.peerConnection.addEventListener("connectionstatechange", (evt) => {
|
||||||
|
if (self.peerConnection.connectionState === 'disconnected') {
|
||||||
|
self.client.signalRemoteDisconnect(self.peerId);
|
||||||
|
} else if (self.peerConnection.connectionState === 'connected') {
|
||||||
|
if (self.client.peerState != PEERSTATE_SUCCESS) self.client.peerState = PEERSTATE_SUCCESS;
|
||||||
|
} else if (self.peerConnection.connectionState === 'failed') {
|
||||||
|
if (self.client.peerState == PEERSTATE_LOADING) self.client.peerState = PEERSTATE_FAILED;
|
||||||
|
self.client.signalRemoteDisconnect(self.peerId);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
disconnect() {
|
||||||
|
if (this.dataChannel != null) {
|
||||||
|
this.dataChannel.close();
|
||||||
|
this.dataChannel = null;
|
||||||
|
}
|
||||||
|
this.peerConnection.close();
|
||||||
|
}
|
||||||
|
|
||||||
|
setRemoteDescription(descJSON) {
|
||||||
|
const self = this;
|
||||||
|
try {
|
||||||
|
const remoteDesc = JSON.parse(descJSON);
|
||||||
|
this.peerConnection.setRemoteDescription(remoteDesc, () => {
|
||||||
|
if (remoteDesc.type == 'offer') {
|
||||||
|
self.peerConnection.createAnswer((desc) => {
|
||||||
|
const selfDesc = desc;
|
||||||
|
self.peerConnection.setLocalDescription(selfDesc, () => {
|
||||||
|
self.client.descriptionHandler(self.peerId, JSON.stringify(selfDesc));
|
||||||
|
if (self.client.peerStateDesc != PEERSTATE_SUCCESS) self.client.peerStateDesc = PEERSTATE_SUCCESS;
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to set local description for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateDesc == PEERSTATE_LOADING) self.client.peerStateDesc = PEERSTATE_FAILED;
|
||||||
|
self.client.signalRemoteDisconnect(self.peerId);
|
||||||
|
});
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to create answer for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateDesc == PEERSTATE_LOADING) self.client.peerStateDesc = PEERSTATE_FAILED;
|
||||||
|
self.client.signalRemoteDisconnect(self.peerId);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}, (err) => {
|
||||||
|
console.error("Failed to set remote description for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateDesc == PEERSTATE_LOADING) self.client.peerStateDesc = PEERSTATE_FAILED;
|
||||||
|
self.client.signalRemoteDisconnect(self.peerId);
|
||||||
|
});
|
||||||
|
} catch (err) {
|
||||||
|
console.error("Failed to parse remote description for \"" + self.peerId + "\"! " + err);
|
||||||
|
if (self.client.peerStateDesc == PEERSTATE_LOADING) self.client.peerStateDesc = PEERSTATE_FAILED;
|
||||||
|
self.client.signalRemoteDisconnect(self.peerId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
addICECandidate(candidates) {
|
||||||
|
try {
|
||||||
|
const candidateList = JSON.parse(candidates);
|
||||||
|
for (let candidate of candidateList) {
|
||||||
|
this.peerConnection.addIceCandidate(new RTCIceCandidate(candidate));
|
||||||
|
}
|
||||||
|
if (this.client.peerStateIce != PEERSTATE_SUCCESS) this.client.peerStateIce = PEERSTATE_SUCCESS;
|
||||||
|
} catch (err) {
|
||||||
|
console.error("Failed to parse ice candidate for \"" + this.peerId + "\"! " + err);
|
||||||
|
if (this.client.peerStateIce == PEERSTATE_LOADING) this.client.peerStateIce = PEERSTATE_FAILED;
|
||||||
|
this.client.signalRemoteDisconnect(this.peerId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class EaglercraftLANServer {
|
||||||
|
|
||||||
|
constructor() {
|
||||||
|
this.ICEServers = [];
|
||||||
|
this.hasInit = false;
|
||||||
|
this.peerList = new Map();
|
||||||
|
this.peerState = PEERSTATE_LOADING;
|
||||||
|
this.peerStateConnect = PEERSTATE_LOADING;
|
||||||
|
this.peerStateInitial = PEERSTATE_LOADING;
|
||||||
|
this.peerStateDesc = PEERSTATE_LOADING;
|
||||||
|
this.peerStateIce = PEERSTATE_LOADING;
|
||||||
|
this.iceCandidateHandler = null;
|
||||||
|
this.descriptionHandler = null;
|
||||||
|
this.remoteClientDataChannelHandler = null;
|
||||||
|
this.remoteClientDisconnectHandler = null;
|
||||||
|
this.remoteClientPacketHandler = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
LANServerSupported() {
|
||||||
|
return typeof window.RTCPeerConnection !== "undefined";
|
||||||
|
}
|
||||||
|
|
||||||
|
initializeServer() {
|
||||||
|
// nothing to do!
|
||||||
|
}
|
||||||
|
|
||||||
|
setICEServers(urls) {
|
||||||
|
this.ICEServers.length = 0;
|
||||||
|
for (var i = 0; i < urls.length; ++i) {
|
||||||
|
var etr = urls[i].split(";");
|
||||||
|
if (etr.length == 1) {
|
||||||
|
this.ICEServers.push({urls: etr[0]});
|
||||||
|
} else if (etr.length == 3) {
|
||||||
|
this.ICEServers.push({urls: etr[0], username: etr[1], credential: etr[2]});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setICECandidateHandler(cb) {
|
||||||
|
this.iceCandidateHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setDescriptionHandler(cb) {
|
||||||
|
this.descriptionHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setRemoteClientDataChannelHandler(cb) {
|
||||||
|
this.remoteClientDataChannelHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setRemoteClientDisconnectHandler(cb) {
|
||||||
|
this.remoteClientDisconnectHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
setRemoteClientPacketHandler(cb) {
|
||||||
|
this.remoteClientPacketHandler = cb;
|
||||||
|
}
|
||||||
|
|
||||||
|
sendPacketToRemoteClient(peerId, buffer) {
|
||||||
|
var thePeer = this.peerList.get(peerId);
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
if (thePeer.dataChannel != null && thePeer.dataChannel.readyState == "open") {
|
||||||
|
thePeer.dataChannel.send(buffer);
|
||||||
|
} else {
|
||||||
|
this.signalRemoteDisconnect(peerId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
resetPeerStates() {
|
||||||
|
this.peerState = this.peerStateConnect = this.peerStateInitial = this.peerStateDesc = this.peerStateIce = PEERSTATE_LOADING;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerState() {
|
||||||
|
return this.peerState;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerStateConnect() {
|
||||||
|
return this.peerStateConnect;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerStateInitial() {
|
||||||
|
return this.peerStateInitial;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerStateDesc() {
|
||||||
|
return this.peerStateDesc;
|
||||||
|
}
|
||||||
|
|
||||||
|
getPeerStateIce() {
|
||||||
|
return this.peerStateIce;
|
||||||
|
}
|
||||||
|
|
||||||
|
signalRemoteConnect(peerId) {
|
||||||
|
try {
|
||||||
|
const peerConnection = new RTCPeerConnection({
|
||||||
|
iceServers: this.ICEServers,
|
||||||
|
optional: [{DtlsSrtpKeyAgreement: true}]
|
||||||
|
});
|
||||||
|
const peerInstance = new EaglercraftLANPeer(this, peerId, peerConnection);
|
||||||
|
this.peerList.set(peerId, peerInstance);
|
||||||
|
if (this.peerStateConnect != PEERSTATE_SUCCESS) this.peerStateConnect = PEERSTATE_SUCCESS;
|
||||||
|
} catch (e) {
|
||||||
|
if (this.peerStateConnect == PEERSTATE_LOADING) this.peerStateConnect = PEERSTATE_FAILED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalRemoteDescription(peerId, descJSON) {
|
||||||
|
var thePeer = this.peerList.get(peerId);
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
thePeer.setRemoteDescription(descJSON);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalRemoteICECandidate(peerId, candidate) {
|
||||||
|
var thePeer = this.peerList.get(peerId);
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
thePeer.addICECandidate(candidate);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
signalRemoteDisconnect(peerId) {
|
||||||
|
if (peerId.length == 0) {
|
||||||
|
for (const thePeer of this.peerList.values()) {
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
this.peerList.delete(peerId);
|
||||||
|
try {
|
||||||
|
thePeer.disconnect();
|
||||||
|
} catch (e) {
|
||||||
|
}
|
||||||
|
this.remoteClientDisconnectHandler(peerId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
this.peerList.clear();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var thePeer = this.peerList.get(peerId);
|
||||||
|
if ((typeof thePeer !== "undefined") && thePeer !== null) {
|
||||||
|
this.peerList.delete(peerId);
|
||||||
|
try {
|
||||||
|
thePeer.disconnect();
|
||||||
|
} catch (e) {
|
||||||
|
}
|
||||||
|
this.remoteClientDisconnectHandler(peerId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
countPeers() {
|
||||||
|
return this.peerList.size;
|
||||||
|
}
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
window.constructLANServer = () => new EaglercraftLANServer();
|
||||||
|
});
|
||||||
|
|
||||||
|
window.startLANServer = () => {
|
||||||
|
if (typeof window.constructLANServer !== "function") {
|
||||||
|
window.initializeLANServer();
|
||||||
|
}
|
||||||
|
return window.constructLANServer();
|
||||||
|
};
|
153
src/game/web/clients/precision/index.html
Normal file
@ -0,0 +1,153 @@
|
|||||||
|
<!doctype html>
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8" />
|
||||||
|
<title>Precision Client</title>
|
||||||
|
<link rel="icon" type="image/webp" href="/resources/images/icons/clients/precision.webp" />
|
||||||
|
<link rel="stylesheet" href="/resources/styles/eagler.css" />
|
||||||
|
<script src="/resources/scripts/google-tag.js"></script>
|
||||||
|
<script src="/game/web/clients/precision/eagswebrtc.js"></script>
|
||||||
|
<script src="/game/web/clients/precision/classes.js"></script>
|
||||||
|
<script async src="/game/web/clients/precision/arc-sw.js"></script>
|
||||||
|
<style>
|
||||||
|
@font-face {
|
||||||
|
font-family: 'Product Sans';
|
||||||
|
src: url(ProductSans.ttf);
|
||||||
|
}
|
||||||
|
|
||||||
|
html {
|
||||||
|
color: #fff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.starter {
|
||||||
|
border-radius: 5px;
|
||||||
|
border: 1px solid #fff;
|
||||||
|
background-color: #0d0c0c;
|
||||||
|
color: #fff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dropdown {
|
||||||
|
position: relative;
|
||||||
|
display: inline-block;
|
||||||
|
border-radius: 5px;
|
||||||
|
border: 1px solid #fff;
|
||||||
|
background-color: #0d0c0c;
|
||||||
|
color: #fff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.gameframe {
|
||||||
|
background-image: url('bg.png');
|
||||||
|
background-size: cover;
|
||||||
|
font-family: 'Product Sans';
|
||||||
|
}
|
||||||
|
|
||||||
|
#Selection {
|
||||||
|
display: inline-block;
|
||||||
|
position: absolute;
|
||||||
|
top: 50%;
|
||||||
|
left: 50%;
|
||||||
|
transform: translate(-50%, -50%);
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
</head>
|
||||||
|
<body id="game_frame" class="gameframe">
|
||||||
|
<div id="Selection">
|
||||||
|
<h1>Precision Client</h1>
|
||||||
|
<h3>Select a texture pack:</h3>
|
||||||
|
<select id="Packs" class="dropdown">
|
||||||
|
<option disabled selected hidden value="">-- Choose one --</option>
|
||||||
|
<option value="defaultold">Default Old</option>
|
||||||
|
<option value="defaultnew">Default 1.17+</option>
|
||||||
|
<option value="bombies">Bombies 180k</option>
|
||||||
|
<option value="bones">Bare Bones</option>
|
||||||
|
<option value="modifiednew">Modified 1.17+</option>
|
||||||
|
<option value="miamiprivate">Miami Private</option>
|
||||||
|
<option value="nebula">Nebula</option>
|
||||||
|
<option value="rhedd">Rhedd</option>
|
||||||
|
<option value="ricefault">Ricefault</option>
|
||||||
|
<option value="tightfault">Tightfault</option>
|
||||||
|
<option value="walifault">Walifault</option>
|
||||||
|
</select>
|
||||||
|
<br /><br />
|
||||||
|
<input class="starter" type="button" value="Launch" onclick="Start();" />
|
||||||
|
</div>
|
||||||
|
<script>
|
||||||
|
'use strict';
|
||||||
|
const PackSelect = document.getElementById('Packs');
|
||||||
|
PackSelect.value = localStorage.getItem('precisionClientLastPack') || '';
|
||||||
|
|
||||||
|
function Start() {
|
||||||
|
if (PackSelect.value) {
|
||||||
|
const Selected = PackSelect.value;
|
||||||
|
document.getElementById('Selection').style.display = 'none';
|
||||||
|
localStorage.setItem('precisionClientLastPack', Selected);
|
||||||
|
|
||||||
|
const relayId = Math.floor(Math.random() * 3);
|
||||||
|
window.eaglercraftOpts = {
|
||||||
|
container: 'game_frame',
|
||||||
|
assetsURI: `${window.location.pathname}/packs/${Selected}.epk`,
|
||||||
|
localesURI: `${window.location.pathname}/lang/`,
|
||||||
|
serverWorkerURI: `${window.location.pathname}/worker_bootstrap.js`,
|
||||||
|
worldsFolder: 'MAIN',
|
||||||
|
servers: [],
|
||||||
|
relays: [
|
||||||
|
{
|
||||||
|
addr: 'wss://relay.deev.is/',
|
||||||
|
name: 'lax1dude relay #1',
|
||||||
|
primary: relayId === 0,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
addr: 'wss://relay.lax1dude.net/',
|
||||||
|
name: 'lax1dude relay #2',
|
||||||
|
primary: relayId === 1,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
addr: 'wss://relay.shhnowisnottheti.me/',
|
||||||
|
name: 'ayunami relay #1',
|
||||||
|
primary: relayId === 2,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
mainMenu: {
|
||||||
|
splashes: [],
|
||||||
|
eaglerLogo: false,
|
||||||
|
},
|
||||||
|
assetOverrides: {
|
||||||
|
'records/wait.mp3': 'wait.mp3',
|
||||||
|
'records/mellohi.mp3':
|
||||||
|
'https://stream.nightride.fm/chillsynth.m4a',
|
||||||
|
'records/far.mp3': 'https://stream.nightride.fm/nightride.m4a',
|
||||||
|
'records/cat.mp3': 'http://usa9.fastcast4u.com/proxy/jamz?mp=/1',
|
||||||
|
'records/ward.mp3': 'http://fr4.1mix.co.uk:8000/192h',
|
||||||
|
'records/strad.mp3': 'http://listen.011fm.com:8028/stream15',
|
||||||
|
'records/blocks.mp3': 'https://www.ophanim.net:8444/s/9780',
|
||||||
|
'records/13.mp3': 'https://s2.radio.co/s2b2b68744/listen',
|
||||||
|
'credits.txt': 'assetoverrides/credits.txt',
|
||||||
|
'precision/gui.png': 'assetoverrides/precision/gui.png',
|
||||||
|
'precision/gui2.png': 'assetoverrides/precision/gui2.png',
|
||||||
|
'precision/guismall.png': 'assetoverrides/precision/guismall.png',
|
||||||
|
'precision/logo.png': 'assetoverrides/precision/logo.png',
|
||||||
|
'precision/precision.png':
|
||||||
|
'assetoverrides/precision/precision.png',
|
||||||
|
'precision/precision2.png':
|
||||||
|
'assetoverrides/precision/precision2.png',
|
||||||
|
'lang/en_US.lang': 'assetoverrides/lang/en_US.lang',
|
||||||
|
'gui/demo_bg.png': 'assetoverrides/gui/demo_bg.png',
|
||||||
|
'title/bg/panorama0.png': 'assetoverrides/title/bg/panorama0.png',
|
||||||
|
'title/bg/panorama1.png': 'assetoverrides/title/bg/panorama1.png',
|
||||||
|
'title/bg/panorama2.png': 'assetoverrides/title/bg/panorama2.png',
|
||||||
|
'title/bg/panorama3.png': 'assetoverrides/title/bg/panorama3.png',
|
||||||
|
'title/bg/panorama4.png': 'assetoverrides/title/bg/panorama4.png',
|
||||||
|
'title/bg/panorama5.png': 'assetoverrides/title/bg/panorama5.png',
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
const urlParams = new URLSearchParams(window.location.search);
|
||||||
|
window.eaglercraftOpts.joinServer =
|
||||||
|
urlParams.get('server') ?? undefined;
|
||||||
|
|
||||||
|
main();
|
||||||
|
} else alert('You need to select a pack');
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
</body>
|
||||||
|
</html>
|
BIN
src/game/web/clients/precision/packs/bombies.epk
Normal file
BIN
src/game/web/clients/precision/packs/bones.epk
Normal file
BIN
src/game/web/clients/precision/packs/defaultnew.epk
Normal file
BIN
src/game/web/clients/precision/packs/defaultold.epk
Normal file
BIN
src/game/web/clients/precision/packs/miamiprivate.epk
Normal file
BIN
src/game/web/clients/precision/packs/modifiednew.epk
Normal file
BIN
src/game/web/clients/precision/packs/rhedd.epk
Normal file
BIN
src/game/web/clients/precision/packs/tightfault.epk
Normal file
BIN
src/game/web/clients/precision/packs/walifault.epk
Normal file
5
src/game/web/clients/precision/worker_bootstrap.js
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
onmessage = function (o) {
|
||||||
|
importScripts("classes_server.js");
|
||||||
|
eaglercraftServerOpts = o.data;
|
||||||
|
main();
|
||||||
|
};
|
@ -1,14 +0,0 @@
|
|||||||
<!DOCTYPE html>
|
|
||||||
<html>
|
|
||||||
<head>
|
|
||||||
<meta charset="UTF-8" />
|
|
||||||
<title>Starlike Client</title>
|
|
||||||
<link rel="icon" type="image/webp" href="/resources/images/icons/clients/starlike.webp" />
|
|
||||||
<link rel="stylesheet" href="/resources/styles/eagler.css" />
|
|
||||||
<script src="/resources/scripts/google-tag.js"></script>
|
|
||||||
<script src="/game/web/clients/starlike/classes.js"></script>
|
|
||||||
<script src="/resources/scripts/eagler-launch/1.8.8/eaglerpocketmobile.js"></script>
|
|
||||||
<script src="/resources/scripts/eagler-launch/1.8.8/main.js"></script>
|
|
||||||
</head>
|
|
||||||
<body id="game_frame"></body>
|
|
||||||
</html>
|
|
@ -1,458 +0,0 @@
|
|||||||
addServer.add=Oti
|
|
||||||
addServer.enterIp=Wāhi noho o te tūmau
|
|
||||||
addServer.enterName=Ingoa o te tūmau
|
|
||||||
addServer.hideAddress=huna wāhitau
|
|
||||||
addServer.resourcePack=Pōkai Rauemi Tūmau
|
|
||||||
addServer.resourcePack.disabled=Monokia
|
|
||||||
addServer.resourcePack.enabled=Mkakaurangi
|
|
||||||
addServer.resourcePack.prompt=Tohuāki
|
|
||||||
addServer.title=Whakatika i te tūmau
|
|
||||||
book.editTitle=Tomo Book Taitara:
|
|
||||||
book.finalizeButton=Tohu me Katia
|
|
||||||
book.finalizeWarning=Kia mōhio mai! A, no te haina koe i te pukapuka, ka kore e taea te reira.
|
|
||||||
book.signButton=Tohu
|
|
||||||
chat.cannotSend=Kāore e taea te tukatuka kōrerorero karere
|
|
||||||
chat.copy=Tārua ki Papatopenga
|
|
||||||
chat.link.confirm=Kei te hiahia koe ki te whakatuwhera i te hononga ki a koutou?
|
|
||||||
chat.link.confirmTrusted=E hiahia ana koe ki te whakatūwhera mai tēnei hono ranei te tārua te reira ki o koutou papatopenga?
|
|
||||||
chat.link.open=Whakatūwhera i roto i te Browser
|
|
||||||
chat.link.warning=Kaua e whakat hononga i tangata ke!
|
|
||||||
chat.stream.emote=(%s) * %s %s
|
|
||||||
chat.stream.text=(%s) <%s> %s
|
|
||||||
chat.type.achievement=%s kua tika roaa te paetae %s
|
|
||||||
connect.authorizing=Takiuru in...
|
|
||||||
connect.connecting=E hono ana ki te tūmau...
|
|
||||||
connect.failed=I rahua te hono ki te tūmau
|
|
||||||
controls.title=Mana
|
|
||||||
createWorld.customize.custom.presets=Tatūkē
|
|
||||||
createWorld.customize.flat.addLayer=tāpiri kahu-
|
|
||||||
createWorld.customize.flat.editLayer=apa whakatika
|
|
||||||
createWorld.customize.flat.height=teitei
|
|
||||||
createWorld.customize.flat.layer.bottom=raro %s
|
|
||||||
createWorld.customize.flat.layer.top=runga -%s
|
|
||||||
createWorld.customize.flat.removeLayer=tango kahu-
|
|
||||||
createWorld.customize.flat.tile=Apa nāunau
|
|
||||||
createWorld.customize.flat.title=Whakaraupapa Superflat
|
|
||||||
createWorld.customize.presets=Tatūkē
|
|
||||||
createWorld.customize.presets.list=Tērā rānei, konei te etahi hanga tatou i mua!
|
|
||||||
createWorld.customize.presets.select=whakamahi tatūkē
|
|
||||||
createWorld.customize.presets.share=E hiahia ana ki te faaite i to koutou tatūkē ki te tangata? Whakamahia te pouaka i raro nei!
|
|
||||||
createWorld.customize.presets.title=tīpako i te tatūkē
|
|
||||||
demo.day.1=Tenei demo ka muri e rima nga ra game, koutou pai te mahi!
|
|
||||||
demo.day.2=ra e rua
|
|
||||||
demo.day.3=ra e toru
|
|
||||||
demo.day.4=ra e wha
|
|
||||||
demo.day.5=Ko koutou ra whakamutunga tenei!
|
|
||||||
demo.day.6=kua mutu e rima nga ra. Press "F5" ki te tango he pikitia o to koutou hanga
|
|
||||||
demo.day.warning=Ko to koutou wa tata ake!
|
|
||||||
demo.demoExpired=Demo oti!
|
|
||||||
demo.help.buy=hoko Minecraft inaianei!
|
|
||||||
demo.help.fullWrapped=Tenei demo ka muri e rima nga ra (e pā ana ki 1 haora me te 40 miniti o te wā tūturu). Tirohia te whakatutukitanga mō ngā tīwhiri! Kia ngahau!
|
|
||||||
demo.help.inventory=Whakamahia %1$s ki te whakatuwhera i tō peke
|
|
||||||
demo.help.jump=Peke mā te pēhi i %1$s
|
|
||||||
demo.help.later=Tonu tākaro!
|
|
||||||
demo.help.movement=Whakamahia %1$s, %2$s, %3$s, %4$s me te kiore ki te neke a tawhio noa
|
|
||||||
demo.help.movementMouse=Titiro huri noa te whakamahi i te kiore
|
|
||||||
demo.help.movementShort=Neke mā te pēhi i %1$s, %2$s, %3$s, %4$s
|
|
||||||
demo.help.title=Aratau Demo Minecraft
|
|
||||||
demo.remainingTime=te wā e toe ana: %s
|
|
||||||
demo.reminder=Kua mutu te demo. te hoko i te kēmu ki te haere tonu tīmata ranei te ao hou!
|
|
||||||
disconnect.closed=katia hononga
|
|
||||||
disconnect.disconnected=Kua momotu i te Tūmau
|
|
||||||
disconnect.endOfStream=Mutunga o te Awa
|
|
||||||
disconnect.kicked=I whana i te kēmu
|
|
||||||
disconnect.loginFailed=I rahua te takiuru
|
|
||||||
disconnect.loginFailedInfo=I rahua te takiuru: %s
|
|
||||||
disconnect.loginFailedInfo.invalidSession=Wātū muhu (Me tīmata anō i tō kēmu)
|
|
||||||
disconnect.loginFailedInfo.serversUnavailable=Ko te motuhēhēnga he wā ki raro mo te tiaki.
|
|
||||||
disconnect.lost=hononga ngaro
|
|
||||||
disconnect.overflow=papare te waipuke
|
|
||||||
disconnect.quitting=whakamutu
|
|
||||||
disconnect.spam=Whana hoki whakamuhani
|
|
||||||
disconnect.timeout=pau i roto i
|
|
||||||
entity.Boat.name=Waka
|
|
||||||
entity.EntityHorse.name=Hoiho
|
|
||||||
entity.horse.name=Hoiho
|
|
||||||
gameMode.adventure=Aratau Adventure
|
|
||||||
gameMode.changed=Kua whakahoutia te gameplay
|
|
||||||
gameMode.creative=Aratau Creative
|
|
||||||
gameMode.hardcore=aratau tino!
|
|
||||||
gameMode.survival=Aratau Survival
|
|
||||||
generator.amplified=ô-
|
|
||||||
generator.amplified.info=pānui: anake hoki ngahau, me nui rorohiko
|
|
||||||
generator.default=taunoa
|
|
||||||
generator.flat=Superflat
|
|
||||||
generator.largeBiomes=ngā wāhi nui
|
|
||||||
gui.all=Katoa
|
|
||||||
gui.back=Hoki
|
|
||||||
gui.cancel=Whakakore
|
|
||||||
gui.done=Oti
|
|
||||||
gui.down=iho
|
|
||||||
gui.no=Kāo
|
|
||||||
gui.toMenu=hoki ki te mata taitara
|
|
||||||
gui.up=Ake
|
|
||||||
gui.yes=Āe
|
|
||||||
item.apple.name=Āporo
|
|
||||||
item.arrow.name=Pere
|
|
||||||
item.bed.name=Moenga
|
|
||||||
item.beefCooked.name=Kotinga mīti
|
|
||||||
item.boat.name=Waka
|
|
||||||
item.bone.name=Wheua
|
|
||||||
item.bow.name=Kopere
|
|
||||||
item.bread.name=Parāoa
|
|
||||||
item.bucket.name=Pēre
|
|
||||||
item.cake.name=Keke
|
|
||||||
item.carrots.name=Kāreti
|
|
||||||
item.charcoal.name=Waro
|
|
||||||
item.clock.name=Karaka
|
|
||||||
item.coal.name=Waro
|
|
||||||
item.compass.name=Kāpehu
|
|
||||||
item.cookie.name=Pihikete
|
|
||||||
item.diamond.name=Taimana
|
|
||||||
item.egg.name=Hēki
|
|
||||||
item.emerald.name=Kahurangi
|
|
||||||
item.feather.name=Piki
|
|
||||||
item.fishingRod.name=Matira
|
|
||||||
item.flint.name=Matā
|
|
||||||
item.hatchetWood.name=Tuaina ki rakau
|
|
||||||
item.ingotGold.name=Gold Ingot
|
|
||||||
item.ingotIron.name=Iron Ingot
|
|
||||||
item.leather.name=Rera
|
|
||||||
item.map.name=Mapi
|
|
||||||
item.painting.name=Waituhi
|
|
||||||
item.pickaxeWood.name=Keriwhenua ki rakau
|
|
||||||
item.saddle.name=Tera
|
|
||||||
item.seeds.name=Purapura
|
|
||||||
item.shovelWood.name=koko rakau
|
|
||||||
item.sign.name=Pouārahi
|
|
||||||
item.snowball.name=Poi huka
|
|
||||||
item.stick.name=Rākau
|
|
||||||
item.sulphur.name=Paura
|
|
||||||
item.swordIron.name=Iron Hoari
|
|
||||||
item.swordWood.name=te hoari rakau
|
|
||||||
item.wheat.name=Wīti
|
|
||||||
key.categories.inventory=Rārangi taonga
|
|
||||||
key.categories.multiplayer=Multiplayer
|
|
||||||
key.inventory=Rārangi taonga
|
|
||||||
key.jump=Peke
|
|
||||||
lanServer.otherPlayers=i ngā tautuhinga mō ētahi atu kaitākaro
|
|
||||||
lanServer.scanning=matawai mō ngā kēmu i runga i tō whatunga rohe
|
|
||||||
lanServer.start=tīmata LAN ao
|
|
||||||
lanServer.title=LAN te ao
|
|
||||||
language.code=mi_NZ
|
|
||||||
language.name=Te Reo Māori
|
|
||||||
language.region=Aotearoa
|
|
||||||
mcoServer.title=hou te ao ipurangi Minecraft
|
|
||||||
menu.convertingLevel=Faafariuraa o te ao
|
|
||||||
menu.disconnect=Wetea
|
|
||||||
menu.game=tahua kēmu
|
|
||||||
menu.generatingLevel=Auaha te ao
|
|
||||||
menu.generatingTerrain=Auaha te whenua
|
|
||||||
menu.loadingLevel=Rāwekeweke te ao
|
|
||||||
menu.multiplayer=huihui
|
|
||||||
menu.options=nga kōwhiringa...
|
|
||||||
menu.playdemo=Te tākaro Demo World
|
|
||||||
menu.quit=Putanga
|
|
||||||
menu.resetdemo=Tautuhi anō Demo World
|
|
||||||
menu.respawning=whakawhānau takarure
|
|
||||||
menu.returnToGame=Hoki ki te kēmu
|
|
||||||
menu.returnToMenu=Putanga me haere ki te rārangi tono
|
|
||||||
menu.shareToLan=tuwhera tō LAN
|
|
||||||
menu.simulating=Construction o te ao i roto i nga paraire
|
|
||||||
menu.singleplayer=anake
|
|
||||||
menu.switchingLevel=Whakawhitiwhiti nga ao
|
|
||||||
multiplayer.connect=Hono
|
|
||||||
multiplayer.downloadingStats=Te tikiake i ngā tatauranga & whakatutukitanga ...
|
|
||||||
multiplayer.downloadingTerrain=Tikiake ana i nga whenua
|
|
||||||
multiplayer.info1=Minecraft Multiplayer kore tēnei wā kei te oti, engari i reira
|
|
||||||
multiplayer.info2=whakamātautau bug wawe puta.
|
|
||||||
multiplayer.ipinfo=Tomo i te IP o te tūmau, ki te hono atu ki reira:
|
|
||||||
multiplayer.player.joined=%s uru atu te kēmu
|
|
||||||
multiplayer.player.joined.renamed=%s (e mōhiotia i mua kia rite ki %s) i uru ki te kēmu
|
|
||||||
multiplayer.player.left=%s mahue te kēmu
|
|
||||||
multiplayer.stopSleeping=waiho Bed
|
|
||||||
multiplayer.texturePrompt.line1=E taunaki ana tēnei tūmau i te whakamahi o te mōkihi rauemi ritenga.
|
|
||||||
multiplayer.texturePrompt.line2=E hiahia ana koe ki te tiki ake me te tāuta i te reira aunoa?
|
|
||||||
multiplayer.title=te tākaro multiplayer
|
|
||||||
options.advancedButton=Settings Ataata Arā...
|
|
||||||
options.advancedOpengl=OpenGL Arā
|
|
||||||
options.advancedVideoTitle=Settings Ataata Arā
|
|
||||||
options.anaglyph=3D Anaglyph
|
|
||||||
options.ao=Whakamumuratanga Whakaene
|
|
||||||
options.ao.max=Mōrahi
|
|
||||||
options.ao.min=Mōkito
|
|
||||||
options.ao.off=OFF
|
|
||||||
options.chat.color=Tae
|
|
||||||
options.chat.height.unfocused=Not Focused Height
|
|
||||||
options.chat.links=Hononga Tukutuku
|
|
||||||
options.chat.links.prompt=Tohuāki i runga i Hononga
|
|
||||||
options.chat.opacity=Opacity
|
|
||||||
options.chat.scale=Tauine
|
|
||||||
options.chat.title=Settings kōrerorero...
|
|
||||||
options.chat.visibility=kōrerorero
|
|
||||||
options.chat.visibility.full=whakaaturia
|
|
||||||
options.chat.visibility.hidden=Huna
|
|
||||||
options.chat.visibility.system=tono anake
|
|
||||||
options.chat.width=Whānuitanga
|
|
||||||
options.controls=Mana...
|
|
||||||
options.difficulty=Uaua
|
|
||||||
options.difficulty.easy=Ngāwari
|
|
||||||
options.difficulty.hard=Māro
|
|
||||||
options.difficulty.hardcore=Hardcore
|
|
||||||
options.difficulty.normal=Pūnoa
|
|
||||||
options.difficulty.peaceful=Rangimārie
|
|
||||||
options.farWarning1=Tūtohutia te tāutanga Java 64 bit te
|
|
||||||
options.farWarning2='Far' hoatu tawhiti (koe 32 bit)
|
|
||||||
options.fboEnable=Whakahohe i FBOs
|
|
||||||
options.fov=FOV
|
|
||||||
options.fov.max=Quake PROV
|
|
||||||
options.fov.min=Pūnoa
|
|
||||||
options.framerateLimit=Mokatere tāpare Max
|
|
||||||
options.framerateLimit.max=Unlimited
|
|
||||||
options.gamma=Gile
|
|
||||||
options.gamma.max=Kanapa
|
|
||||||
options.gamma.min=Moody
|
|
||||||
options.graphics=Whakairoiro
|
|
||||||
options.graphics.fancy=Fancy
|
|
||||||
options.graphics.fast=Nohopuku
|
|
||||||
options.guiScale=GUI Tauine
|
|
||||||
options.guiScale.auto=Car
|
|
||||||
options.guiScale.large=Nui
|
|
||||||
options.guiScale.normal=Pūnoa
|
|
||||||
options.guiScale.small=Iti
|
|
||||||
options.hidden=Huna
|
|
||||||
options.invertMouse=Huripoki Kiore
|
|
||||||
options.language=Reo...
|
|
||||||
options.languageWarning=E kore ai translations reo e tōtika 100%%
|
|
||||||
options.multiplayer.title=Settings Multiplayer...
|
|
||||||
options.music=Puoro
|
|
||||||
options.off=OFF
|
|
||||||
options.on=ON
|
|
||||||
options.particles=matūriki
|
|
||||||
options.particles.all=Katoa
|
|
||||||
options.particles.decreased=Heke
|
|
||||||
options.particles.minimal=Iti
|
|
||||||
options.performanceButton=Settings Mahinga Ataata...
|
|
||||||
options.performanceVideoTitle=Settings Mahinga Ataata
|
|
||||||
options.postButton=Settings Post-Processing...
|
|
||||||
options.postProcessEnable=Whakahohetia te Post-Processing
|
|
||||||
options.postVideoTitle=Settings Post-Processing
|
|
||||||
options.qualityButton=Settings Kounga Ataata...
|
|
||||||
options.qualityVideoTitle=Settings Kounga Ataata
|
|
||||||
options.renderClouds=Kapua
|
|
||||||
options.renderDistance=Hoatu tawhiti
|
|
||||||
options.renderDistance.far=Tawhiti
|
|
||||||
options.renderDistance.normal=Pūnoa
|
|
||||||
options.renderDistance.short=Poto
|
|
||||||
options.renderDistance.tiny=Iti
|
|
||||||
options.saturation=waiwai
|
|
||||||
options.sensitivity=Rauangi
|
|
||||||
options.sensitivity.max=HYPERSPEED!!!
|
|
||||||
options.sensitivity.min=*Oha*
|
|
||||||
options.snooper=Tukua popore
|
|
||||||
options.sound=tangi
|
|
||||||
options.sounds=Music & Oro...
|
|
||||||
options.sounds.title=Kōwhiringa Music & Sound
|
|
||||||
options.stream=Pāohotanga Settings...
|
|
||||||
options.stream.changes=Me tīmata anō pea koutou awa koe mo ki enei rerekētanga tango i te wahi.
|
|
||||||
options.stream.compression.high=Tiketike
|
|
||||||
options.stream.compression.low=Iti
|
|
||||||
options.stream.compression.medium=Waenga
|
|
||||||
options.stream.mic_toggle.talk=Kōrero
|
|
||||||
options.title=kōwhiringa
|
|
||||||
options.video=Settings Video...
|
|
||||||
options.videoTitle=Settings Video
|
|
||||||
options.viewBobbing=Tirohia te whāwhā
|
|
||||||
options.visible=whakaaturia
|
|
||||||
record.nowPlaying=tākaro Na: %s
|
|
||||||
selectServer.add=Tāpiri Tūmau
|
|
||||||
selectServer.defaultName=Tūmau Minecraft
|
|
||||||
selectServer.delete=Porowhiu
|
|
||||||
selectServer.deleteButton=Porowhiu
|
|
||||||
selectServer.deleteQuestion=Whakaū i te tango o tenei tūmau?
|
|
||||||
selectServer.deleteWarning=Ngaro ka ake ake! (Te wa i!)
|
|
||||||
selectServer.direct=Whakarerekē
|
|
||||||
selectServer.edit=Whakarerekē
|
|
||||||
selectServer.empty=tahanga
|
|
||||||
selectServer.hiddenAddress=(Huna)
|
|
||||||
selectServer.refresh=Update
|
|
||||||
selectServer.select=amui atu tūmau
|
|
||||||
selectServer.title=te tīpako i te tūmau
|
|
||||||
selectWorld.allowCommands=Tuku i te whakahau:
|
|
||||||
selectWorld.allowCommands.info=Kainga, herehere, i ētahi atu momo ao... /gamemode, /xp
|
|
||||||
selectWorld.bonusItems=utu uma:
|
|
||||||
selectWorld.cheats=Tinihanga
|
|
||||||
selectWorld.conversion=Me tahuri!
|
|
||||||
selectWorld.create=Waihanga he world new
|
|
||||||
selectWorld.createDemo=Te tākaro New Demo World
|
|
||||||
selectWorld.customizeType=Whakatauritea
|
|
||||||
selectWorld.delete=Porowhiu
|
|
||||||
selectWorld.deleteButton=Porowhiu
|
|
||||||
selectWorld.deleteQuestion=E hiahia ana koe ki te muku i tēnei ao ki a koutou?
|
|
||||||
selectWorld.deleteWarning=ka ngaro ake ake! (He roa te wā!)
|
|
||||||
selectWorld.empty=tahanga
|
|
||||||
selectWorld.enterName=ingoa ao
|
|
||||||
selectWorld.enterSeed=uri mo te kaihanga ao
|
|
||||||
selectWorld.gameMode=Aratau Game
|
|
||||||
selectWorld.gameMode.adventure=Haere māia
|
|
||||||
selectWorld.gameMode.adventure.line1=Rite aratau ora, engari e kore e taea e poraka
|
|
||||||
selectWorld.gameMode.adventure.line2=tāpiri, te tango ranei,
|
|
||||||
selectWorld.gameMode.creative=auaha
|
|
||||||
selectWorld.gameMode.creative.line1=rauemi mure ore, e rere ana, me te kore utu
|
|
||||||
selectWorld.gameMode.creative.line2=Top -%s
|
|
||||||
selectWorld.gameMode.hardcore=tino
|
|
||||||
selectWorld.gameMode.hardcore.line1=Rite aratau ora, kua kiia i faingataa
|
|
||||||
selectWorld.gameMode.hardcore.line2=uaua, a kotahi te ora anake
|
|
||||||
selectWorld.gameMode.survival=Noho ora
|
|
||||||
selectWorld.gameMode.survival.line1=Rapu mō te rauemi, ke fokotuutuu, taonga
|
|
||||||
selectWorld.gameMode.survival.line2=taumata, te hauora, me te matekai
|
|
||||||
selectWorld.hardcoreMode=tino:
|
|
||||||
selectWorld.hardcoreMode.info=mukua ao te ki runga ki te mate
|
|
||||||
selectWorld.mapFeatures=Whakaputa hanganga:
|
|
||||||
selectWorld.mapFeatures.info=Kainga, herehere, i ētahi atu momo ao
|
|
||||||
selectWorld.mapType=Momo o te ao:
|
|
||||||
selectWorld.mapType.normal=Noa
|
|
||||||
selectWorld.moreWorldOptions=Ētahi atu Kōwhiringa Ao ...
|
|
||||||
selectWorld.newWorld=ao hou
|
|
||||||
selectWorld.newWorld.copyOf=kape o te %s
|
|
||||||
selectWorld.recreate=Waihangatia tētahi atu wā
|
|
||||||
selectWorld.rename=Huria te ingoa
|
|
||||||
selectWorld.renameButton=whakaingoa
|
|
||||||
selectWorld.renameTitle=whakaingoa World
|
|
||||||
selectWorld.resultFolder=ka ora i roto i:
|
|
||||||
selectWorld.seedInfo=waiho kia pātea tonu hoki te uri tupurangi
|
|
||||||
selectWorld.select=Te tākaro i te ao kua tīpakohia
|
|
||||||
selectWorld.title=Tīpakohia te ao
|
|
||||||
selectWorld.world=Ao
|
|
||||||
soundCategory.ambient=Ambient / Taiao
|
|
||||||
soundCategory.block=poraka
|
|
||||||
soundCategory.hostile=Vaerua kaikiri
|
|
||||||
soundCategory.master=rōrahi te Kaiwhakaako
|
|
||||||
soundCategory.music=Puoro
|
|
||||||
soundCategory.neutral=Vaerua hoa
|
|
||||||
soundCategory.player=kaitākaro
|
|
||||||
soundCategory.record=Poraka rekoata / Tuhipoka
|
|
||||||
soundCategory.weather=Weather
|
|
||||||
tile.activatorRail.name=Activator Rail
|
|
||||||
tile.anvil.name=Paepae maitai
|
|
||||||
tile.bedrock.name=maka tefito
|
|
||||||
tile.blockCoal.name=Poraka o Coal
|
|
||||||
tile.blockDiamond.name=Poraka o Diamond
|
|
||||||
tile.bookshelf.name=PukaPuka
|
|
||||||
tile.brick.name=Pereki
|
|
||||||
tile.button.name=Pātene
|
|
||||||
tile.cake.name=Keke
|
|
||||||
tile.carrots.name=Kāreti
|
|
||||||
tile.chest.name=pouaka
|
|
||||||
tile.chestTrap.name=aaka mau
|
|
||||||
tile.cloth.name=Wūru
|
|
||||||
tile.cocoa.name=Koukou
|
|
||||||
tile.crops.name=Kai
|
|
||||||
tile.deadbush.name=mate Bush
|
|
||||||
tile.detectorRail.name=pūkimi Rail
|
|
||||||
tile.dirt.default.name=Oneone
|
|
||||||
tile.dirt.podzol.name=Onemata
|
|
||||||
tile.doorIron.name=Iron Door
|
|
||||||
tile.doorWood.name=Door Rakau
|
|
||||||
tile.doublePlant.fern.name=Ponga
|
|
||||||
tile.doublePlant.rose.name=Rōha
|
|
||||||
tile.doublePlant.sunflower.name=Putiputi rā
|
|
||||||
tile.farmland.name=Papanga pāmu
|
|
||||||
tile.fence.name=Taiepa
|
|
||||||
tile.fire.name=Ahi
|
|
||||||
tile.flower1.dandelion.name=Tawao
|
|
||||||
tile.flower2.allium.name=Allium
|
|
||||||
tile.flower2.houstonia.name=Azure Bluet
|
|
||||||
tile.flower2.tulipRed.name=Whero Tulip
|
|
||||||
tile.furnace.name=Oumu
|
|
||||||
tile.glass.name=Karaehe
|
|
||||||
tile.goldenRail.name=Rail Powered
|
|
||||||
tile.grass.name=tarutaru Poraka
|
|
||||||
tile.gravel.name=Tuakirikiri
|
|
||||||
tile.hayBlock.name=hay wuru
|
|
||||||
tile.ice.name=Haupapa
|
|
||||||
tile.ladder.name=Arawhata
|
|
||||||
tile.lava.name=Tahepuia
|
|
||||||
tile.leaves.acacia.name=hitimi Rau
|
|
||||||
tile.leaves.big_oak.name=Dark Oak Rau
|
|
||||||
tile.leaves.birch.name=birch Rau
|
|
||||||
tile.leaves.jungle.name=uru raau no Rau
|
|
||||||
tile.leaves.name=Ngā rau
|
|
||||||
tile.leaves.oak.name=Rau oki
|
|
||||||
tile.leaves.spruce.name=Rau te puruhi
|
|
||||||
tile.lever.name=Ara
|
|
||||||
tile.log.acacia.name=hitimi Wood
|
|
||||||
tile.log.big_oak.name=Dark Oak Wood
|
|
||||||
tile.log.birch.name=Birch Wood
|
|
||||||
tile.log.jungle.name=uru raau no Wood
|
|
||||||
tile.log.name=Rākau
|
|
||||||
tile.log.oak.name=Rākau oke
|
|
||||||
tile.log.spruce.name=te puruhi mo Wood
|
|
||||||
tile.mobSpawner.name=Monster Spawner
|
|
||||||
tile.obsidian.name=Matā
|
|
||||||
tile.oreCoal.name=Coal Ore
|
|
||||||
tile.oreDiamond.name=Diamond Ore
|
|
||||||
tile.oreGold.name=Gold Ore
|
|
||||||
tile.oreIron.name=Iron Ore
|
|
||||||
tile.potatoes.name=Rīwai
|
|
||||||
tile.pumpkin.name=Paukena
|
|
||||||
tile.rail.name=Ara tereina
|
|
||||||
tile.redstoneDust.name=Redstone puehu
|
|
||||||
tile.sand.default.name=Kirikiri
|
|
||||||
tile.sand.red.name=Kirikiri whero
|
|
||||||
tile.sandStone.chiseled.name=whaoa hōanga
|
|
||||||
tile.sandStone.default.name=Hōanga
|
|
||||||
tile.sandStone.name=Hōanga
|
|
||||||
tile.sandStone.smooth.name=hōanga Whakaene
|
|
||||||
tile.sapling.acacia.name=hitimi Māhuri
|
|
||||||
tile.sapling.birch.name=Birch Māhuri
|
|
||||||
tile.sapling.jungle.name=uru raau no Māhuri
|
|
||||||
tile.sapling.oak.name=Oak Māhuri
|
|
||||||
tile.sapling.spruce.name=te puruhi mo Māhuri
|
|
||||||
tile.sign.name=Tohu
|
|
||||||
tile.snow.name=Huka
|
|
||||||
tile.stainedGlass.black.name=Black ōpure koata
|
|
||||||
tile.stainedGlass.blue.name=Blue ōpure koata
|
|
||||||
tile.stainedGlass.brown.name=Brown ōpure koata
|
|
||||||
tile.stainedGlass.cyan.name=Urikiko ōpure koata
|
|
||||||
tile.stainedGlass.gray.name=Gray ōpure koata
|
|
||||||
tile.stainedGlass.green.name=Green ōpure koata
|
|
||||||
tile.stainedGlass.name=ōpure koata
|
|
||||||
tile.stainedGlass.pink.name=Pink ōpure koata
|
|
||||||
tile.stainedGlass.purple.name=Papura ōpure koata
|
|
||||||
tile.stainedGlass.red.name=Whero ōpure koata
|
|
||||||
tile.stainedGlass.silver.name=Light Gray ōpure koata
|
|
||||||
tile.stairsSandStone.name=hōanga Arawhata
|
|
||||||
tile.stairsStone.name=Stone Arawhata
|
|
||||||
tile.stairsWood.name=Oak Wood Arawhata
|
|
||||||
tile.stairsWoodAcacia.name=Hitimi Wood Arawhata
|
|
||||||
tile.stairsWoodBirch.name=Birch Wood Arawhata
|
|
||||||
tile.stairsWoodDarkOak.name=Dark Oak Wood Arawhata
|
|
||||||
tile.stairsWoodJungle.name=Uru raau no Wood Arawhata
|
|
||||||
tile.stairsWoodSpruce.name=Te puruhi mo Wood Arawhata
|
|
||||||
tile.stoneMoss.name=Moss Stone
|
|
||||||
tile.stonebrick.name=Cobblestone
|
|
||||||
tile.tallgrass.fern.name=Ponga
|
|
||||||
tile.tallgrass.grass.name=Karaihe
|
|
||||||
tile.tallgrass.name=Karaihe
|
|
||||||
tile.tallgrass.shrub.name=Riki
|
|
||||||
tile.thinGlass.name=Pihanga
|
|
||||||
tile.tnt.name=TNT
|
|
||||||
tile.torch.name=Rama
|
|
||||||
tile.water.name=Wai
|
|
||||||
tile.weightedPlate_heavy.name=Plate Pressure tautaha (Taumaha)
|
|
||||||
tile.weightedPlate_light.name=Plate Pressure tautaha (Light)
|
|
||||||
tile.wood.acacia.name=Hitimi Wood papa
|
|
||||||
tile.wood.big_oak.name=Dark Oak Wood papa
|
|
||||||
tile.wood.birch.name=Birch Wood papa
|
|
||||||
tile.wood.jungle.name=Uru raau no Wood papa
|
|
||||||
tile.wood.name=papa rākau
|
|
||||||
tile.wood.oak.name=Oak papa rakau
|
|
||||||
tile.wood.spruce.name=Te puruhi mo Wood papa
|
|
||||||
tile.woodSlab.acacia.name=Hitimi Wood papa
|
|
||||||
tile.woodSlab.big_oak.name=Dark Oak Wood papa
|
|
||||||
tile.woodSlab.birch.name=Birch Wood Papa
|
|
||||||
tile.woodSlab.jungle.name=Uru raau no Wood papa
|
|
||||||
tile.woodSlab.oak.name=Oak Wood Papa
|
|
||||||
tile.woodSlab.spruce.name=Te puruhi mo Wood papa
|
|
||||||
tile.workbench.name=Papamahi
|
|
@ -1,436 +0,0 @@
|
|||||||
achievement.bakeCake=Gielis
|
|
||||||
achievement.bakeCake.desc=Nisut, sohkar, mielki ja monit!
|
|
||||||
achievement.blazeRod=Dollii
|
|
||||||
achievement.bookcase=Girjerájusbargi
|
|
||||||
achievement.buildBetterPickaxe=Buoredat
|
|
||||||
achievement.diamonds=DIAMÁNTTAT!
|
|
||||||
achievement.killWither=Álgu.
|
|
||||||
achievement.spawnWither=Álgu?
|
|
||||||
achievement.theEnd=Loahppa?
|
|
||||||
achievement.theEnd2=Loahppa.
|
|
||||||
addServer.add=Gárvvis
|
|
||||||
attribute.name.generic.movementSpeed=Johtilvuohta
|
|
||||||
book.finalizeButton=Sivdnidat ja dahppat
|
|
||||||
book.generation.0=Originála
|
|
||||||
book.signButton=Sivdnidat
|
|
||||||
chat.stream.emote=(%s) * %s %s
|
|
||||||
chat.stream.text=(%s) <%s> %s
|
|
||||||
commands.ban.failed=Ii máhte gieldit čuojaheadji %s
|
|
||||||
commands.ban.success=Čuojaheaddji %s lea gieldán
|
|
||||||
commands.ban.usage=/ban <nama> [sivva...]
|
|
||||||
commands.clone.usage=/clone <x1> <y1> <z1> <x2> <y2> <z2> <x> <y> <z> [mode]
|
|
||||||
commands.compare.usage=/testforblocks <x1> <y1> <z1> <x2> <y2> <z2><x><y><z>[mode]
|
|
||||||
commands.defaultgamemode.usage=/defaultgamemode <modus>
|
|
||||||
commands.deop.failed=Ii máhte de-op %s
|
|
||||||
commands.deop.usage=/deop <čuojaheadji>
|
|
||||||
commands.difficulty.usage=/difficulty <ođđa áŧestus>
|
|
||||||
commands.entitydata.noPlayers=%s lea čuojaheaddji ja ii máhte rievdaduvvot
|
|
||||||
commands.gamemode.usage=/gamemode <modus> [čuojaheaddji]
|
|
||||||
commands.generic.usage=Geavahus: %s
|
|
||||||
commands.kick.usage=/kick <čuojaheadji> [sivva...]
|
|
||||||
commands.message.display.incoming=%s savkala dutnje: %s
|
|
||||||
commands.message.display.outgoing=Don savkalat čuojaheaddjai %s: %s
|
|
||||||
commands.op.failed=Ii máhte op %s
|
|
||||||
commands.op.usage=/op <čuojaheadji>
|
|
||||||
commands.particle.usage=/particle <name> <x> <y> <z> <xd> <yd> <zd> <speed> [count] [mode]
|
|
||||||
commands.say.usage=/say <dieđáhus>
|
|
||||||
commands.scoreboard.teams.add.alreadyExists=Joavku namain %s juo gávdno
|
|
||||||
commands.scoreboard.teams.add.success=Joavku '%s' lea lasihan
|
|
||||||
commands.scoreboard.teams.leave.noTeam=Don it leat joavkkus
|
|
||||||
commands.scoreboard.teams.list.entry=- %1$s: čájáhusanamma '%2$s', čuojaheaddjit %3$s
|
|
||||||
commands.scoreboard.teams.list.player.empty=Eai leat čuojaheaddjit joavkkus %s
|
|
||||||
commands.scoreboard.teams.list.usage=/scoreboard teams list [namma]
|
|
||||||
commands.scoreboard.teams.option.usage=/scoreboard teams option <team> <friendlyfire|color|seeFriendlyInvisibles|nametagVisibility|deathMessageVisibility> <value>
|
|
||||||
commands.scoreboard.teams.remove.success=Joavku %s lea sihkkon
|
|
||||||
commands.seed.success=Seed: %s
|
|
||||||
commands.setworldspawn.usage=/setworldspawn [<x> <y> <z>]
|
|
||||||
commands.stats.block.usage=/stats block <x> <y> <z> <mode> ...
|
|
||||||
commands.testfor.success=%s lea gávdnan
|
|
||||||
commands.time.query=Diibmu lea %s
|
|
||||||
commands.title.usage.clear=/title <čuojaheaddji> clear|reset
|
|
||||||
commands.unban.failed=Ii máhte eahpegieldit čuojaheadji %s
|
|
||||||
commands.unban.success=Čuojaheaddji %s lea eahpegieldán
|
|
||||||
commands.unban.usage=/pardon <nama>
|
|
||||||
commands.unbanip.usage=/pardon-ip <adreassa>
|
|
||||||
commands.whitelist.add.usage=/whitelist add <čuojaheadji>
|
|
||||||
commands.whitelist.remove.usage=/whitelist sihko <čuojaheadji>
|
|
||||||
commands.worldborder.center.usage=/worldborder center <x> <z>
|
|
||||||
container.enchant.clue=%s . . . ?
|
|
||||||
container.furnace=Steaikauvdna
|
|
||||||
container.isLocked=%s lea lohkkadan!
|
|
||||||
createWorld.customize.custom.confirmTitle=Varuhus!
|
|
||||||
createWorld.customize.custom.next=Viidáseappot
|
|
||||||
createWorld.customize.custom.preset.goodLuck=Ollu lihkku
|
|
||||||
createWorld.customize.custom.preset.isleLand=Sulloeatnan
|
|
||||||
createWorld.customize.custom.preset.waterWorld=Čázi máilbmi
|
|
||||||
createWorld.customize.custom.prev=Ruoktu
|
|
||||||
createWorld.customize.custom.riverSize=Joga sturrodat
|
|
||||||
createWorld.customize.custom.useCaves=Čiehppasat
|
|
||||||
createWorld.customize.custom.useLavaLakes=Lava jávrrit
|
|
||||||
createWorld.customize.custom.useRavines=Ruččut
|
|
||||||
createWorld.customize.custom.useTemples=Tempelat
|
|
||||||
createWorld.customize.custom.useVillages=Gávpogat
|
|
||||||
createWorld.customize.custom.useWaterLakes=Čázi jávrrit
|
|
||||||
createWorld.customize.flat.height=Allodat
|
|
||||||
createWorld.customize.flat.layer.bottom=Bodni - %s
|
|
||||||
createWorld.customize.flat.layer.top=Giera + %s
|
|
||||||
death.attack.generic=%1$s jámii
|
|
||||||
deathScreen.score=Čuoggát
|
|
||||||
deathScreen.title=Don leat jábmi!
|
|
||||||
demo.day.2=Nubbi beaivi
|
|
||||||
demo.day.3=Goalmmát beaivi
|
|
||||||
demo.day.4=Njealját beaivi
|
|
||||||
demo.day.5=Dát lea du maŋimus beaivi!
|
|
||||||
demo.help.buy=Oasttát dál!
|
|
||||||
demo.help.later=Joatkkát ja čuojahat!
|
|
||||||
disconnect.quitting=Guođđit
|
|
||||||
disconnect.timeout=Mihkkege vástádus
|
|
||||||
enchantment.level.1=I
|
|
||||||
enchantment.level.10=X
|
|
||||||
enchantment.level.2=II
|
|
||||||
enchantment.level.3=III
|
|
||||||
enchantment.level.4=IV
|
|
||||||
enchantment.level.5=V
|
|
||||||
enchantment.level.6=VI
|
|
||||||
enchantment.level.7=VII
|
|
||||||
enchantment.level.8=VIII
|
|
||||||
enchantment.level.9=IX
|
|
||||||
entity.Boat.name=Fanas
|
|
||||||
entity.Cat.name=Bussá
|
|
||||||
entity.Chicken.name=Vuonccis
|
|
||||||
entity.Cow.name=Gussa
|
|
||||||
entity.Creeper.name=Creeper
|
|
||||||
entity.EntityHorse.name=Heasta
|
|
||||||
entity.Item.name=Diŋga
|
|
||||||
entity.Pig.name=Spiidni
|
|
||||||
entity.Rabbit.name=Kaniidna
|
|
||||||
entity.Sheep.name=Sávza
|
|
||||||
entity.SnowMan.name=Čagigolem
|
|
||||||
entity.Spider.name=Heavdni
|
|
||||||
entity.Villager.librarian=Girjerájusbargi
|
|
||||||
entity.VillagerGolem.name=Ruovddigolem
|
|
||||||
entity.Wolf.name=Gumpe
|
|
||||||
entity.Zombie.name=Zombi
|
|
||||||
entity.generic.name=dovdameahttun
|
|
||||||
entity.horse.name=Heasta
|
|
||||||
entity.zombiehorse.name=Zombi heasta
|
|
||||||
gameMode.adventure=Máinasmodus
|
|
||||||
gameMode.hardcore=Hardcore-modus!
|
|
||||||
gui.all=Buot
|
|
||||||
gui.back=Ruoktu
|
|
||||||
gui.cancel=Šluhtte
|
|
||||||
gui.done=Gárvvis
|
|
||||||
gui.down=vulos
|
|
||||||
gui.no=Ii
|
|
||||||
gui.none=Ii mihkkege
|
|
||||||
gui.stats=Statistihkat
|
|
||||||
gui.toMenu=Ruoktu váldufálus
|
|
||||||
gui.up=Bajás
|
|
||||||
gui.yes=Gal
|
|
||||||
inventory.binSlot=Billistát diŋgga
|
|
||||||
item.apple.name=Eappel
|
|
||||||
item.banner.black.name=Čáhppat leavga
|
|
||||||
item.banner.blue.name=Alit leavga
|
|
||||||
item.banner.brown.name=Ruškat leavga
|
|
||||||
item.banner.gray.name=Ránis leavga
|
|
||||||
item.banner.green.name=Ruoná leavga
|
|
||||||
item.banner.mojang.black=Čáhppat ášši
|
|
||||||
item.banner.mojang.blue=Alit ášši
|
|
||||||
item.banner.mojang.brown=Ruškat ášši
|
|
||||||
item.banner.mojang.gray=Ránis ášši
|
|
||||||
item.banner.mojang.green=Ruoná ášši
|
|
||||||
item.banner.mojang.orange=Oránša ášši
|
|
||||||
item.banner.mojang.pink=Guvgesruoksa ášši
|
|
||||||
item.banner.mojang.purple=Sáhppat ášši
|
|
||||||
item.banner.mojang.red=Ruoksat ášši
|
|
||||||
item.banner.mojang.white=Vielgat ášši
|
|
||||||
item.banner.mojang.yellow=Fiskat ášši
|
|
||||||
item.banner.orange.name=Oránša leavga
|
|
||||||
item.banner.pink.name=Guvgesruoksat leavga
|
|
||||||
item.banner.purple.name=Sáhppat leavga
|
|
||||||
item.banner.red.name=Ruoksat leavga
|
|
||||||
item.banner.small_stripes.black=Čáhppat ráidá
|
|
||||||
item.banner.small_stripes.blue=Alit ráidá
|
|
||||||
item.banner.small_stripes.brown=Ruškat
|
|
||||||
ráidá
|
|
||||||
item.banner.small_stripes.gray=Ránis ráidá
|
|
||||||
item.banner.small_stripes.green=Ruoná ráidá
|
|
||||||
item.banner.small_stripes.orange=Oránša ráidá
|
|
||||||
item.banner.small_stripes.pink=Guvgeruoksat ráidá
|
|
||||||
item.banner.small_stripes.purple=Sáhppat ráidá
|
|
||||||
item.banner.small_stripes.red=Ruoksat ráidá
|
|
||||||
item.banner.small_stripes.white=Vielgat ráidá
|
|
||||||
item.banner.small_stripes.yellow=Fiskat ráidá
|
|
||||||
item.banner.straight_cross.black=Čáhppat ruossa
|
|
||||||
item.banner.straight_cross.blue=Alit ruossa
|
|
||||||
item.banner.straight_cross.brown=Ruškat ruossa
|
|
||||||
item.banner.straight_cross.gray=Ránis ruossa
|
|
||||||
item.banner.straight_cross.green=Ruoná ruossa
|
|
||||||
item.banner.straight_cross.orange=Oránša ruossa
|
|
||||||
item.banner.straight_cross.pink=Guvgesruoksat ruossa
|
|
||||||
item.banner.straight_cross.purple=Sáhppat ruossa
|
|
||||||
item.banner.straight_cross.red=Ruoksat ruossa
|
|
||||||
item.banner.straight_cross.white=Vielgat ruossa
|
|
||||||
item.banner.straight_cross.yellow=Fiskat ruossa
|
|
||||||
item.banner.white.name=Vielgat leavga
|
|
||||||
item.banner.yellow.name=Fiskat leavga
|
|
||||||
item.bed.name=Seaŋga
|
|
||||||
item.boat.name=Fanas
|
|
||||||
item.book.name=Girji
|
|
||||||
item.bow.name=Dávgi
|
|
||||||
item.bowl.name=Bolljá
|
|
||||||
item.bread.name=Láibi
|
|
||||||
item.bucket.name=Skállu
|
|
||||||
item.bucketLava.name=Lavaskállu
|
|
||||||
item.bucketWater.name=Čáziskállu
|
|
||||||
item.cake.name=Gáhkku
|
|
||||||
item.clay.name=láira
|
|
||||||
item.cookie.name=Keaksa
|
|
||||||
item.diamond.name=Diamántta
|
|
||||||
item.egg.name=Monni
|
|
||||||
item.feather.name=Dávgi
|
|
||||||
item.fireworksCharge.black=Čáhppat
|
|
||||||
item.fireworksCharge.blue=Alit
|
|
||||||
item.fireworksCharge.gray=Ránis
|
|
||||||
item.fireworksCharge.green=Ruoná
|
|
||||||
item.fireworksCharge.orange=Oránša
|
|
||||||
item.fireworksCharge.red=Ruoksat
|
|
||||||
item.fireworksCharge.white=Vielgat
|
|
||||||
item.hatchetDiamond.name=Diamántta-ákšu
|
|
||||||
item.hatchetGold.name=Golliákšu
|
|
||||||
item.hatchetIron.name=Ruovddiákšu
|
|
||||||
item.hatchetStone.name=Geađggiákšu
|
|
||||||
item.hatchetWood.name=Muorra-ákšu
|
|
||||||
item.leaves.name=Lasttat
|
|
||||||
item.map.name=Gárta
|
|
||||||
item.melon.name=Melovdna
|
|
||||||
item.milk.name=Mielki
|
|
||||||
item.paper.name=Bábir
|
|
||||||
item.pickaxeDiamond.name=Diamánttaguohkki
|
|
||||||
item.pickaxeGold.name=Golliguohkki
|
|
||||||
item.pickaxeIron.name=Ruovddiguohkki
|
|
||||||
item.pickaxeStone.name=Geađggiguohkki
|
|
||||||
item.pickaxeWood.name=Muorraguohkki
|
|
||||||
item.potion.name=Juhkamuš
|
|
||||||
item.record.11.desc=C418 - 11
|
|
||||||
item.record.13.desc=C418 - 13
|
|
||||||
item.record.blocks.desc=C418 - blocks
|
|
||||||
item.record.cat.desc=C418 - cat
|
|
||||||
item.record.chirp.desc=C418 - chirp
|
|
||||||
item.record.far.desc=C418 - far
|
|
||||||
item.record.mall.desc=C418 - mall
|
|
||||||
item.record.mellohi.desc=C418 - mellohi
|
|
||||||
item.record.stal.desc=C418 - stal
|
|
||||||
item.record.strad.desc=C418 - strad
|
|
||||||
item.record.wait.desc=C418 - wait
|
|
||||||
item.record.ward.desc=C418 - ward
|
|
||||||
item.redstone.name=Ruoksatgeađgi
|
|
||||||
item.saddle.name=Sále
|
|
||||||
item.sign.name=Galba
|
|
||||||
item.skull.char.name=Oaivi
|
|
||||||
item.skull.creeper.name=Creeper oaivi
|
|
||||||
item.skull.player.name=Čuojaheadji %s oaivi
|
|
||||||
item.skull.zombie.name=Zombi oaivi
|
|
||||||
item.stick.name=Sággi
|
|
||||||
item.sugar.name=Sohkar
|
|
||||||
item.sulphur.name=Rukta
|
|
||||||
item.swordDiamond.name=Diamánttamiehkki
|
|
||||||
item.swordGold.name=Gollimiehkki
|
|
||||||
item.swordIron.name=Ruovddimiehkki
|
|
||||||
item.swordStone.name=Geađggimiehkki
|
|
||||||
item.swordWood.name=Muorramiehkki
|
|
||||||
itemGroup.combat=Dáistaleapmi
|
|
||||||
itemGroup.food=Borramuš
|
|
||||||
itemGroup.redstone= Ruoksatgeađgi
|
|
||||||
itemGroup.tools=Reaiddut
|
|
||||||
key.categories.movement=Johtu
|
|
||||||
key.jump=Njuiket
|
|
||||||
key.mouseButton=Boallu %1$s
|
|
||||||
key.playerlist=Čuojaheadjelistu
|
|
||||||
key.sprint=Viegat
|
|
||||||
lanServer.title=LAN máilbmi
|
|
||||||
language.code=sme
|
|
||||||
language.name=Davvisámegiella
|
|
||||||
language.region=Sápmi
|
|
||||||
menu.disconnect=Guođe
|
|
||||||
menu.options=Heivehusat...
|
|
||||||
menu.quit=Guođe spealus
|
|
||||||
menu.returnToGame=Ruoktu spealluin
|
|
||||||
menu.switchingLevel=Molssut máilmmiid
|
|
||||||
multiplayer.connect=Čanat
|
|
||||||
multiplayer.downloadingTerrain=Viežžá eanadaga
|
|
||||||
multiplayer.player.joined=%s lea laktásan spealu
|
|
||||||
multiplayer.player.left=%s guđii spealus
|
|
||||||
multiplayer.stopSleeping=Guođđit seaŋggas
|
|
||||||
options.ao.off=II ALDE
|
|
||||||
options.blockAlternatives=Molssoeavttolaččat blohkat
|
|
||||||
options.chat.color=Ivnnit
|
|
||||||
options.chat.visibility.hidden=Čiegus
|
|
||||||
options.chat.width=Viidodat
|
|
||||||
options.difficulty=Áŧestus
|
|
||||||
options.difficulty.easy=Geahpas
|
|
||||||
options.difficulty.hard=Lossat
|
|
||||||
options.difficulty.hardcore=Hardcore
|
|
||||||
options.difficulty.normal=Normála
|
|
||||||
options.difficulty.peaceful= Ráfálaš
|
|
||||||
options.fov.max=Quake Pro
|
|
||||||
options.fov.min=Normála
|
|
||||||
options.graphics=Grafihkka
|
|
||||||
options.graphics.fancy=Fiinnis
|
|
||||||
options.graphics.fast=Johtil
|
|
||||||
options.guiScale.auto=Automáhtalaš
|
|
||||||
options.guiScale.large=Stuoris
|
|
||||||
options.guiScale.normal=Normála
|
|
||||||
options.guiScale.small=Uhcci
|
|
||||||
options.hidden=Čiegus
|
|
||||||
options.language=Giella...
|
|
||||||
options.modelPart.cape=Gákti
|
|
||||||
options.modelPart.hat=Háhtta
|
|
||||||
options.modelPart.jacket=Jáhkka
|
|
||||||
options.music=Musihkka
|
|
||||||
options.off=II ALDE
|
|
||||||
options.on=ALDE
|
|
||||||
options.particles=Partihkalat
|
|
||||||
options.particles.all=Buot
|
|
||||||
options.renderClouds=Balvvat
|
|
||||||
options.renderDistance.far=Viiddis
|
|
||||||
options.renderDistance.normal=Normála
|
|
||||||
options.renderDistance.short=Oanehaš
|
|
||||||
options.renderDistance.tiny=Smávis
|
|
||||||
options.sensitivity.max=HYPERJOHTIL!!!
|
|
||||||
options.sound=Jienat
|
|
||||||
options.sounds=Musihkka ja jienat...
|
|
||||||
options.stream.bytesPerPixel=Dássu
|
|
||||||
options.stream.chat.enabled.always=Álo
|
|
||||||
options.stream.chat.enabled.never=Ii goassige
|
|
||||||
options.stream.chat.userFilter=Geavaheadjifilttar
|
|
||||||
options.stream.mic_toggle.mute=Váidudat
|
|
||||||
options.stream.mic_toggle.talk=Humat
|
|
||||||
options.title=Heivehusat
|
|
||||||
potion.damageBoost=Vuoibmi
|
|
||||||
potion.digSpeed=Hoahppu
|
|
||||||
potion.hunger=Nealgi
|
|
||||||
potion.moveSpeed=Johtilvuohta
|
|
||||||
potion.poison=Mirko
|
|
||||||
potion.potency.1=II
|
|
||||||
potion.potency.2=III
|
|
||||||
potion.potency.3=IV
|
|
||||||
potion.prefix.mundane=Dábálaš
|
|
||||||
potion.prefix.uninteresting=Ahkit
|
|
||||||
selectServer.delete=Sihko
|
|
||||||
selectServer.deleteButton=Sihko
|
|
||||||
selectServer.edit=Rievdádeapmi
|
|
||||||
selectServer.empty=guoros
|
|
||||||
selectServer.hiddenAddress=(Čiegus)
|
|
||||||
selectWorld.create=Luova ođđasa máilmmi
|
|
||||||
selectWorld.delete=Sihko
|
|
||||||
selectWorld.deleteButton=Sihko
|
|
||||||
selectWorld.empty=guoros
|
|
||||||
selectWorld.enterName=Máilmmi namma
|
|
||||||
selectWorld.gameMode=Spealumodus
|
|
||||||
selectWorld.gameMode.adventure=Máinnas
|
|
||||||
selectWorld.gameMode.creative=Kreatiiva
|
|
||||||
selectWorld.gameMode.hardcore=Hardcore
|
|
||||||
selectWorld.hardcoreMode=Hardcore:
|
|
||||||
selectWorld.mapType=Máilmmi tiipa:
|
|
||||||
selectWorld.mapType.normal=Normála
|
|
||||||
selectWorld.moreWorldOptions=Eanet máilmmiheivehusat...
|
|
||||||
selectWorld.newWorld=Ođđa máilbmi
|
|
||||||
selectWorld.newWorld.copyOf="%s" máŋggus
|
|
||||||
selectWorld.rename=Attát ođđasa nama
|
|
||||||
selectWorld.renameButton=Attát ođđasa nama
|
|
||||||
selectWorld.renameTitle=Attát máilbmái ođđasa nama
|
|
||||||
selectWorld.title=Vállje máilmmi
|
|
||||||
selectWorld.world=Máilbmi
|
|
||||||
soundCategory.block=Blohkat
|
|
||||||
soundCategory.music=Musihkka
|
|
||||||
soundCategory.player=Čuojaheaddjit
|
|
||||||
soundCategory.weather=Dálki
|
|
||||||
stat.itemsButton=Diŋggat
|
|
||||||
stream.unavailable.initialization_failure.extra=(Sivva: %s)
|
|
||||||
stream.unavailable.no_fbo.version=Dál don atnát: %s
|
|
||||||
stream.unavailable.not_supported.mac.okay=Buoredat
|
|
||||||
stream.unavailable.report_to_mojang=Dieđihát Mojangai
|
|
||||||
stream.user.mode.banned=Gieldán
|
|
||||||
stream.user.mode.banned.other=Gieldán %s gulahallangaskaoamis
|
|
||||||
stream.user.mode.banned.self=Gieldán du gulahallangaskaoamis
|
|
||||||
stream.user.mode.broadcaster=Doaimmaheaddji
|
|
||||||
stream.user.mode.broadcaster.other=Doaimmaheaddji
|
|
||||||
stream.user.mode.broadcaster.self=Doaimmaheaddji (Don!)
|
|
||||||
stream.userinfo.ban=Gielddát
|
|
||||||
stream.userinfo.unban=Eahpegielddát
|
|
||||||
tile.anvil.intact.name=Stáđđi
|
|
||||||
tile.anvil.name=Stáđđi
|
|
||||||
tile.barrier.name=Eastta
|
|
||||||
tile.bed.name=Seaŋga
|
|
||||||
tile.blockCoal.name=Hilablohkka
|
|
||||||
tile.blockDiamond.name=Diamánttablohkka
|
|
||||||
tile.blockGold.name=Golliblohkka
|
|
||||||
tile.blockIron.name=Ruovddiblohkka
|
|
||||||
tile.blockRedstone.name=Ruoksatgeađggiblohkka
|
|
||||||
tile.brick.name=Tiillat
|
|
||||||
tile.cake.name=Gáhkku
|
|
||||||
tile.carrots.name=Rušppit
|
|
||||||
tile.clay.name=láira
|
|
||||||
tile.cloth.black.name=Čáhppat ullu
|
|
||||||
tile.cloth.blue.name=Alit ullu
|
|
||||||
tile.cloth.brown.name=Ruškat ullu
|
|
||||||
tile.cloth.gray.name=Ránis ullu
|
|
||||||
tile.cloth.green.name=Ruoná ullu
|
|
||||||
tile.cloth.name=Ullu
|
|
||||||
tile.cloth.orange.name=Oránša ullu
|
|
||||||
tile.cloth.pink.name=Guvgesruoksat ullu
|
|
||||||
tile.cloth.purple.name=Sáhppat ullu
|
|
||||||
tile.cloth.red.name=Ruoksat ullu
|
|
||||||
tile.cloth.white.name=Ullu
|
|
||||||
tile.cloth.yellow.name=Fiskat ullu
|
|
||||||
tile.cocoa.name=Kakáo
|
|
||||||
tile.dirt.coarse.name=Roavis eana
|
|
||||||
tile.dirt.default.name=Eana
|
|
||||||
tile.dirt.name=Eana
|
|
||||||
tile.doublePlant.name=Šaddu
|
|
||||||
tile.fire.name=Dolla
|
|
||||||
tile.flower1.name=Lieđđi
|
|
||||||
tile.flower2.name=Lieđđi
|
|
||||||
tile.glass.name=Glássa
|
|
||||||
tile.gravel.name=Čievra
|
|
||||||
tile.ice.name=Jiekŋa
|
|
||||||
tile.lava.name=Lava
|
|
||||||
tile.leaves.name=Lasttat
|
|
||||||
tile.litpumpkin.name=Gurbetlikta
|
|
||||||
tile.log.name=Muorra
|
|
||||||
tile.melon.name=Melovdna
|
|
||||||
tile.mushroom.name=Guoppar
|
|
||||||
tile.potatoes.name=Buđeitad
|
|
||||||
tile.pumpkin.name=Gurbbet
|
|
||||||
tile.redSandStone.chiseled.name=Luokčan Ruoksat Sáttogeađgi
|
|
||||||
tile.redSandStone.default.name=Ruoksat Sáttogeađgi
|
|
||||||
tile.redSandStone.name=Ruoksat Sáttogeađgi
|
|
||||||
tile.sand.default.name=Sáttu
|
|
||||||
tile.sand.name=Sáttu
|
|
||||||
tile.sand.red.name=Ruoksat sáttu
|
|
||||||
tile.sandStone.chiseled.name=Luokčan sáttogeađgi
|
|
||||||
tile.sandStone.default.name=Sáttogeađgi
|
|
||||||
tile.sandStone.name=Sáttogeađgi
|
|
||||||
tile.sign.name=Galba
|
|
||||||
tile.sponge.dry.name=Guopparas
|
|
||||||
tile.sponge.wet.name=Njuoskkas guopparas
|
|
||||||
tile.stone.stone.name=Geađgi
|
|
||||||
tile.tallgrass.grass.name=Rássi
|
|
||||||
tile.tallgrass.name=Rássi
|
|
||||||
tile.tallgrass.shrub.name=Miestta
|
|
||||||
tile.tnt.name=TNT
|
|
||||||
tile.torch.name=Spáiddar
|
|
||||||
tile.water.name=Čáhci
|
|
||||||
tile.woolCarpet.black.name=Čáhppat lávdebeaitta
|
|
||||||
tile.woolCarpet.blue.name=Alit lávdebeaitta
|
|
||||||
tile.woolCarpet.brown.name=Ruškat lávdebeaitta
|
|
||||||
tile.woolCarpet.gray.name=Ránis lávdebeaitta
|
|
||||||
tile.woolCarpet.green.name=Ruoná lávdebeaitta
|
|
||||||
tile.woolCarpet.name=Lávdebeaitta
|
|
||||||
tile.woolCarpet.orange.name=Oránša lávdebeaitta
|
|
||||||
tile.woolCarpet.pink.name=Guvgesruoksat lávdebeaitta
|
|
||||||
tile.woolCarpet.purple.name=Sáhppat lávdebeaitta
|
|
||||||
tile.woolCarpet.red.name=Ruoksat lávdebeaitta
|
|
||||||
tile.woolCarpet.white.name=Lávdebeaitta
|
|
||||||
tile.woolCarpet.yellow.name=Fiskat lávdebeaitta
|
|