First commit
|
@ -0,0 +1,47 @@
|
|||
## Generic ignorable patterns and files
|
||||
*~
|
||||
.*.swp
|
||||
*bak*
|
||||
tags
|
||||
*.vim
|
||||
|
||||
## Non-static Minetest directories
|
||||
/build*
|
||||
/bin/
|
||||
/games/*
|
||||
!/games/minetest/
|
||||
!/games/minimal/
|
||||
/cache/
|
||||
/textures/
|
||||
/sounds/
|
||||
/mods/*
|
||||
!/mods/minetest/
|
||||
/mods/minetest/*
|
||||
!/mods/minetest/mods_here.txt
|
||||
/worlds/
|
||||
/world/
|
||||
|
||||
## Configuration/log files
|
||||
minetest.conf
|
||||
debug.txt
|
||||
|
||||
## Build files
|
||||
CMakeFiles/*
|
||||
src/CMakeFiles/*
|
||||
src/Makefile
|
||||
src/cmake_config.h
|
||||
src/cmake_install.cmake
|
||||
src/jthread/CMakeFiles/*
|
||||
src/jthread/Makefile
|
||||
src/jthread/cmake_config.h
|
||||
src/jthread/cmake_install.cmake
|
||||
src/jthread/libjthread.a
|
||||
src/lua/build/
|
||||
src/lua/CMakeFiles/
|
||||
CMakeCache.txt
|
||||
CPackConfig.cmake
|
||||
CPackSourceConfig.cmake
|
||||
Makefile
|
||||
cmake_install.cmake
|
||||
locale/
|
||||
|
|
@ -0,0 +1,171 @@
|
|||
cmake_minimum_required(VERSION 2.6)
|
||||
if(${CMAKE_VERSION} STREQUAL "2.8.2")
|
||||
# bug http://vtk.org/Bug/view.php?id=11020
|
||||
message( WARNING "CMake/CPack version 2.8.2 will not create working .deb packages!")
|
||||
endif(${CMAKE_VERSION} STREQUAL "2.8.2")
|
||||
|
||||
# This can be read from ${PROJECT_NAME} after project() is called
|
||||
project(minetest)
|
||||
|
||||
set(VERSION_EXTRA "" CACHE STRING "Stuff to append to version string")
|
||||
|
||||
# Also remember to set PROTOCOL_VERSION in clientserver.h when releasing
|
||||
set(VERSION_MAJOR 0)
|
||||
set(VERSION_MINOR 4)
|
||||
set(VERSION_PATCH dev-20120408)
|
||||
if(VERSION_EXTRA)
|
||||
set(VERSION_PATCH ${VERSION_PATCH}-${VERSION_EXTRA})
|
||||
endif()
|
||||
set(VERSION_STRING "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}")
|
||||
|
||||
MESSAGE(STATUS "*** Will build version ${VERSION_STRING} ***")
|
||||
|
||||
# Configuration options
|
||||
|
||||
if(WIN32)
|
||||
set(RUN_IN_PLACE 1 CACHE BOOL "Run directly in source directory structure")
|
||||
else()
|
||||
set(RUN_IN_PLACE 0 CACHE BOOL "Run directly in source directory structure")
|
||||
endif()
|
||||
|
||||
set(BUILD_CLIENT 1 CACHE BOOL "Build client")
|
||||
if(WIN32)
|
||||
set(BUILD_SERVER 0 CACHE BOOL "Build server")
|
||||
else()
|
||||
set(BUILD_SERVER 1 CACHE BOOL "Build server")
|
||||
endif()
|
||||
|
||||
set(WARN_ALL 1 CACHE BOOL "Enable -Wall for Release build")
|
||||
|
||||
if(NOT CMAKE_BUILD_TYPE)
|
||||
# Default to release
|
||||
set(CMAKE_BUILD_TYPE Release CACHE STRING "Build type: Debug or Release" FORCE)
|
||||
endif()
|
||||
|
||||
# Included stuff
|
||||
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/Modules/")
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Modules/misc.cmake)
|
||||
|
||||
# This is done here so that relative search paths are more reasnable
|
||||
find_package(Irrlicht)
|
||||
find_package(CURL)
|
||||
|
||||
#
|
||||
# Installation
|
||||
#
|
||||
|
||||
if(WIN32)
|
||||
set(SHAREDIR ".")
|
||||
set(BINDIR "bin")
|
||||
set(DOCDIR "doc")
|
||||
set(EXAMPLE_CONF_DIR ".")
|
||||
set(LOCALEDIR "locale")
|
||||
elseif(APPLE)
|
||||
# Random placeholders; this isn't usually used and may not work
|
||||
# See https://github.com/toabi/minetest-mac/
|
||||
set(SHAREDIR "share/${PROJECT_NAME}")
|
||||
set(BINDIR "bin")
|
||||
set(DOCDIR "share/doc/${PROJECT_NAME}")
|
||||
set(EXAMPLE_CONF_DIR ${DOCDIR})
|
||||
set(LOCALEDIR "locale")
|
||||
elseif(UNIX) # Linux, BSD etc
|
||||
if(RUN_IN_PLACE)
|
||||
set(SHAREDIR ".")
|
||||
set(BINDIR "bin")
|
||||
set(DOCDIR "doc")
|
||||
set(EXAMPLE_CONF_DIR ".")
|
||||
set(MANDIR "unix/man")
|
||||
set(XDG_APPS_DIR "unix/applications")
|
||||
set(ICONDIR "unix/icons")
|
||||
set(LOCALEDIR "locale")
|
||||
else()
|
||||
set(SHAREDIR "share/${PROJECT_NAME}")
|
||||
set(BINDIR "bin")
|
||||
set(DOCDIR "share/doc/${PROJECT_NAME}")
|
||||
set(MANDIR "share/man")
|
||||
set(EXAMPLE_CONF_DIR ${DOCDIR})
|
||||
set(XDG_APPS_DIR "share/applications")
|
||||
set(ICONDIR "share/icons")
|
||||
set(LOCALEDIR "share/locale")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/builtin" DESTINATION "${SHAREDIR}")
|
||||
#install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/games/minimal" DESTINATION "${SHAREDIR}/games")
|
||||
set(MINETEST_GAME_SOURCE "${CMAKE_CURRENT_SOURCE_DIR}/games/minetest")
|
||||
if(EXISTS ${MINETEST_GAME_SOURCE} AND IS_DIRECTORY ${MINETEST_GAME_SOURCE})
|
||||
install(FILES ${MINETEST_GAME_SOURCE}/game.conf DESTINATION "${SHAREDIR}/games/minetest_game/")
|
||||
install(FILES ${MINETEST_GAME_SOURCE}/README.txt DESTINATION "${SHAREDIR}/games/minetest_game/")
|
||||
install(DIRECTORY ${MINETEST_GAME_SOURCE}/mods DESTINATION "${SHAREDIR}/games/minetest_game")
|
||||
endif()
|
||||
if(BUILD_CLIENT)
|
||||
#install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/sounds/base/pack" DESTINATION "${SHAREDIR}/sounds/base")
|
||||
install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/textures/base/pack" DESTINATION "${SHAREDIR}/textures/base")
|
||||
endif()
|
||||
if(RUN_IN_PLACE)
|
||||
install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/mods/minetest/mods_here.txt" DESTINATION "${SHAREDIR}/mods/minetest")
|
||||
install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/textures/all/textures_here.txt" DESTINATION "${SHAREDIR}/textures/all")
|
||||
endif()
|
||||
|
||||
install(FILES "README.md" DESTINATION "${DOCDIR}")
|
||||
install(FILES "doc/lua_api.txt" DESTINATION "${DOCDIR}")
|
||||
install(FILES "doc/mapformat.txt" DESTINATION "${DOCDIR}")
|
||||
install(FILES "minetest.conf.example" DESTINATION "${EXAMPLE_CONF_DIR}")
|
||||
|
||||
if(UNIX)
|
||||
install(FILES "doc/minetest.6" "doc/minetestserver.6" DESTINATION "${MANDIR}/man6")
|
||||
install(FILES "misc/minetest.desktop" DESTINATION "${XDG_APPS_DIR}")
|
||||
install(FILES "misc/minetest-icon.svg" DESTINATION "${ICONDIR}/hicolor/scalable/apps")
|
||||
endif()
|
||||
|
||||
#
|
||||
# Subdirectories
|
||||
# Be sure to add all relevant definitions above this
|
||||
#
|
||||
|
||||
add_subdirectory(src)
|
||||
|
||||
# CPack
|
||||
|
||||
set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "An InfiniMiner/Minecraft inspired game")
|
||||
set(CPACK_PACKAGE_VERSION_MAJOR ${VERSION_MAJOR})
|
||||
set(CPACK_PACKAGE_VERSION_MINOR ${VERSION_MINOR})
|
||||
set(CPACK_PACKAGE_VERSION_PATCH ${VERSION_PATCH})
|
||||
set(CPACK_PACKAGE_VENDOR "celeron55")
|
||||
set(CPACK_PACKAGE_CONTACT "Perttu Ahola <celeron55@gmail.com>")
|
||||
|
||||
if(WIN32)
|
||||
# For some reason these aren't copied otherwise
|
||||
# NOTE: For some reason now it seems to work without these
|
||||
#if(BUILD_CLIENT)
|
||||
# install(FILES bin/minetest.exe DESTINATION bin)
|
||||
#endif()
|
||||
#if(BUILD_SERVER)
|
||||
# install(FILES bin/minetestserver.exe DESTINATION bin)
|
||||
#endif()
|
||||
|
||||
set(CPACK_PACKAGE_FILE_NAME "${PROJECT_NAME}-${VERSION_STRING}-win32")
|
||||
|
||||
set(CPACK_GENERATOR ZIP)
|
||||
|
||||
# This might be needed for some installer
|
||||
#set(CPACK_PACKAGE_EXECUTABLES bin/minetest.exe "Minetest" bin/minetestserver.exe "Minetest Server")
|
||||
elseif(APPLE)
|
||||
# TODO
|
||||
# see http://cmake.org/Wiki/CMake:CPackPackageGenerators#Bundle_.28OSX_only.29
|
||||
#
|
||||
set(CPACK_PACKAGE_FILE_NAME "${PROJECT_NAME}-${VERSION_STRING}-osx")
|
||||
set(CPACK_PACKAGE_ICON "")
|
||||
set(CPACK_BUNDLE_NAME ${PROJECT_NAME})
|
||||
set(CPACK_BUNDLE_ICON "")
|
||||
set(CPACK_BUNDLE_PLIST "")
|
||||
set(CPACK_BUNDLE_STARTUP_COMMAND "Contents/MacOS/${PROJECT_NAME}")
|
||||
set(CPACK_GENERATOR "Bundle")
|
||||
else()
|
||||
set(CPACK_PACKAGE_FILE_NAME "${PROJECT_NAME}-${VERSION_STRING}-linux")
|
||||
set(CPACK_GENERATOR TGZ)
|
||||
set(CPACK_SOURCE_GENERATOR TGZ)
|
||||
endif()
|
||||
|
||||
include(CPack)
|
||||
|
|
@ -0,0 +1,338 @@
|
|||
Minetest++
|
||||
==========
|
||||
|
||||
A game built off of the best free and open source Minecraft clone, Minetest-C55.
|
||||
|
||||
Copyright (c) 2010-2012 Perttu Ahola <celeron55@gmail.com>
|
||||
and ther contributors (see source file comments and the version control log)
|
||||
|
||||
This contains 2 different game modes, Minetest and Minimal.
|
||||
Game mode Minimal is just a test and will be taken out soon. Game mode Minetest has all the cool features.
|
||||
|
||||
Further documentation
|
||||
----------------------
|
||||
- Website: http://www.minetest.net
|
||||
- Wiki: http://wiki.minetest.com
|
||||
- Forum: http://www.minetest.net/forum
|
||||
|
||||
This game is in alpha!
|
||||
--------------------------
|
||||
- Don't expect it to work as well as a finished game will.
|
||||
- Please tell me about any bugs you come across. Just look in your debug.txt file. (/minetest/bin/debug.txt)
|
||||
- But other then that, have fun and expect new features :)
|
||||
|
||||
Default Controls
|
||||
-----------------
|
||||
- WASD: Move
|
||||
- Space: Jump
|
||||
- E:
|
||||
- While walking: Run (need the fast privelage)
|
||||
- While flying: Go down
|
||||
- Shift: Sneak
|
||||
- Q: Drop item
|
||||
- R: Open inventory
|
||||
- Mouse: Turn/look
|
||||
- C: Toggle fly (need fly privelage)
|
||||
- X: toggle fast (need fast Privelage)
|
||||
- Settable in the configuration file, see the section below.
|
||||
|
||||
Compiling:
|
||||
-----------------------
|
||||
### GNU/Linux ###
|
||||
#### Install dependencies. ####
|
||||
Here's an example for Debian/Ubuntu:
|
||||
`sudo apt-get install build-essential libirrlicht-dev cmake libbz2-dev libpng12-dev libjpeg8-dev libxxf86vm-dev libgl1-mesa-dev libsqlite3-dev libogg-dev libvorbis-dev libopenal-dev`
|
||||
|
||||
#### Download source: ####
|
||||
|
||||
##### Method 1: Download tarball #####
|
||||
|
||||
wget https://github.com/jordan4ibanez/minetest/tarball/master -O master.tar.gz
|
||||
tar xf master.tar.gz
|
||||
cd jordan4ibanez-minetest-*
|
||||
|
||||
##### Method 2: Clone from git #####
|
||||
|
||||
git clone git://github.com/jordan4ibanez/minetest.git minetestpp
|
||||
cd minetestpp
|
||||
|
||||
#### Build ####
|
||||
|
||||
##### Method 1: Build a version that runs directly from the source directory #####
|
||||
|
||||
cmake . -DRUN_IN_PLACE=1
|
||||
make -j2
|
||||
|
||||
##### Method 2: Build a version that can be installed system-wide #####
|
||||
|
||||
mkdir build && cd build
|
||||
cmake ..
|
||||
make
|
||||
sudo make install
|
||||
|
||||
- Use cmake . -LH to see all CMake options and their current state
|
||||
- If you want to install it system-wide (or are making a distribution package), you will want to use -DRUN_IN_PLACE=0
|
||||
- You can build a bare server or a bare client by specifying -DBUILD_CLIENT=0 or -DBUILD_SERVER=0
|
||||
- You can select between Release and Debug build by -DCMAKE_BUILD_TYPE=<Debug or Release>
|
||||
- Debug build is slower, but gives much more useful output in a debugger
|
||||
|
||||
### Windows :###
|
||||
- This section is outdated. In addition to what is described here:
|
||||
- In addition to minetest, you need to download minetest_game.
|
||||
- If you wish to have sound support, you need libogg, libvorbis and libopenal
|
||||
|
||||
- You need:
|
||||
* CMake:
|
||||
http://www.cmake.org/cmake/resources/software.html
|
||||
* MinGW or Visual Studio
|
||||
http://www.mingw.org/
|
||||
http://msdn.microsoft.com/en-us/vstudio/default
|
||||
* Irrlicht SDK 1.7:
|
||||
http://irrlicht.sourceforge.net/downloads.html
|
||||
* Zlib headers (zlib125.zip)
|
||||
http://www.winimage.com/zLibDll/index.html
|
||||
* Zlib library (zlibwapi.lib and zlibwapi.dll from zlib125dll.zip):
|
||||
http://www.winimage.com/zLibDll/index.html
|
||||
* Optional: gettext bibrary and tools:
|
||||
http://gnuwin32.sourceforge.net/downlinks/gettext.php
|
||||
- This is used for other UI languages. Feel free to leave it out.
|
||||
* And, of course, Minetest-c55:
|
||||
http://c55.me/minetest/download
|
||||
- Steps:
|
||||
- Select a directory called DIR hereafter in which you will operate.
|
||||
- Make sure you have CMake and a compiler installed.
|
||||
- Download all the other stuff to DIR and extract them into there.
|
||||
("extract here", not "extract to packagename/")
|
||||
NOTE: zlib125dll.zip needs to be extracted into zlib125dll
|
||||
- All those packages contain a nice base directory in them, which
|
||||
should end up being the direct subdirectories of DIR.
|
||||
- You will end up with a directory structure like this:
|
||||
+ DIR
|
||||
- zlib-1.2.5.tar.gz
|
||||
- zlib125dll.zip
|
||||
- irrlicht-1.7.1.zip
|
||||
- 110214175330.zip (or whatever, this is the minetest source)
|
||||
+ zlib-1.2.5
|
||||
- zlib.h
|
||||
+ win32
|
||||
...
|
||||
+ zlib125dll
|
||||
- readme.txt
|
||||
+ dll32
|
||||
...
|
||||
+ irrlicht-1.7.1
|
||||
+ lib
|
||||
+ include
|
||||
...
|
||||
+ gettext (optional)
|
||||
+bin
|
||||
+include
|
||||
+lib
|
||||
+ minetest
|
||||
+ src
|
||||
+ doc
|
||||
- CMakeLists.txt
|
||||
- Start up the CMake GUI
|
||||
- Select "Browse Source..." and select DIR/minetest
|
||||
- Now, if using MSVC:
|
||||
- Select "Browse Build..." and select DIR/minetest-build
|
||||
- Else if using MinGW:
|
||||
- Select "Browse Build..." and select DIR/minetest
|
||||
- Select "Configure"
|
||||
- Select your compiler
|
||||
- It will warn about missing stuff, ignore that at this point. (later don't)
|
||||
- Make sure the configuration is as follows (note that the versions may differ for you):</li><pre><code>-----------------
|
||||
BUILD_CLIENT [X]
|
||||
BUILD_SERVER [ ]
|
||||
CMAKE_BUILD_TYPE Release
|
||||
CMAKE_INSTALL_PREFIX DIR/minetest-install
|
||||
IRRLICHT_SOURCE_DIR DIR/irrlicht-1.7.1
|
||||
RUN_IN_PLACE [X]
|
||||
WARN_ALL [ ]
|
||||
ZLIB_DLL DIR/zlib125dll/dll32/zlibwapi.dll
|
||||
ZLIB_INCLUDE_DIR DIR/zlib-1.2.5
|
||||
ZLIB_LIBRARIES DIR/zlib125dll/dll32/zlibwapi.lib
|
||||
GETTEXT_BIN_DIR DIR/gettext/bin
|
||||
GETTEXT_INCLUDE_DIR DIR/gettext/include
|
||||
GETTEXT_LIBRARIES DIR/gettext/lib/intl.lib
|
||||
GETTEXT_MSGFMT DIR/gettext/bin/msgfmt
|
||||
-----------------</code></pre>
|
||||
- Hit "Configure"
|
||||
- Hit "Configure" once again 8)
|
||||
- If something is still coloured red, you have a problem.
|
||||
- Hit "Generate"
|
||||
If using MSVC:
|
||||
- Open the generated minetest.sln
|
||||
- The project defaults to the "Debug" configuration. Make very sure to
|
||||
select "Release", unless you want to debug some stuff (it's slower
|
||||
and might not even work at all)
|
||||
- Build the ALL_BUILD project
|
||||
- Build the INSTALL project
|
||||
- You should now have a working game with the executable in
|
||||
DIR/minetest-install/bin/minetest.exe
|
||||
- Additionally you may create a zip package by building the PACKAGE
|
||||
project.
|
||||
If using MinGW:
|
||||
- Using the command line, browse to the build directory and run 'make'
|
||||
(or mingw32-make or whatever it happens to be)
|
||||
- You may need to copy some of the downloaded DLLs into bin/, see what
|
||||
running the produced executable tells you it doesn't have.
|
||||
- You should now have a working game with the executable in
|
||||
DIR/minetest/bin/minetest.exe
|
||||
|
||||
#### This can be automated with a batch script like this ###
|
||||
|
||||
set sourcedir=%CD%
|
||||
set installpath="C:\tmp\minetest_install"
|
||||
set irrlichtpath="C:\tmp\irrlicht-1.7.2"
|
||||
|
||||
set builddir=%sourcedir%\bvc10
|
||||
mkdir %builddir%
|
||||
pushd %builddir%
|
||||
cmake %sourcedir% -G "Visual Studio 10" -DIRRLICHT_SOURCE_DIR=%irrlichtpath% -DRUN_IN_PLACE=1 -DCMAKE_INSTALL_PREFIX=%installpath%
|
||||
if %errorlevel% neq 0 goto fail
|
||||
"C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\MSBuild.exe" ALL_BUILD.vcxproj /p:Configuration=Release
|
||||
if %errorlevel% neq 0 goto fail
|
||||
"C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\MSBuild.exe" INSTALL.vcxproj /p:Configuration=Release
|
||||
if %errorlevel% neq 0 goto fail
|
||||
"C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\MSBuild.exe" PACKAGE.vcxproj /p:Configuration=Release
|
||||
if %errorlevel% neq 0 goto fail
|
||||
popd
|
||||
echo Finished.
|
||||
exit /b 0
|
||||
|
||||
:fail
|
||||
popd
|
||||
echo Failed.
|
||||
exit /b 1
|
||||
|
||||
License of Minetest-c55 textures and sounds
|
||||
-------------------------------------------
|
||||
|
||||
This applies to textures and sounds contained in the main Minetest
|
||||
distribution.
|
||||
|
||||
Attribution-ShareAlike 3.0 Unported (CC BY-SA 3.0)
|
||||
http://creativecommons.org/licenses/by-sa/3.0/
|
||||
|
||||
License of Minetest-c55 source code
|
||||
-----------------------------------
|
||||
|
||||
Minetest-c55
|
||||
Copyright (C) 2010-2011 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along
|
||||
with this program; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
|
||||
Irrlicht
|
||||
---------------
|
||||
|
||||
This program uses the Irrlicht Engine. http://irrlicht.sourceforge.net/
|
||||
|
||||
The Irrlicht Engine License
|
||||
|
||||
Copyright © 2002-2005 Nikolaus Gebhardt
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute
|
||||
it freely, subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you
|
||||
must not claim that you wrote the original software. If you use
|
||||
this software in a product, an acknowledgment in the product
|
||||
documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must
|
||||
not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source
|
||||
distribution.
|
||||
|
||||
|
||||
JThread
|
||||
---------------
|
||||
|
||||
This program uses the JThread library. License for JThread follows:
|
||||
|
||||
Copyright (c) 2000-2006 Jori Liesenborgs (jori.liesenborgs@gmail.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a
|
||||
copy of this software and associated documentation files (the "Software"),
|
||||
to deal in the Software without restriction, including without limitation
|
||||
the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
and/or sell copies of the Software, and to permit persons to whom the
|
||||
Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included
|
||||
in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
||||
IN THE SOFTWARE.
|
||||
|
||||
Lua
|
||||
---------------
|
||||
|
||||
Lua is licensed under the terms of the MIT license reproduced below.
|
||||
This means that Lua is free software and can be used for both academic
|
||||
and commercial purposes at absolutely no cost.
|
||||
|
||||
For details and rationale, see http://www.lua.org/license.html .
|
||||
|
||||
Copyright (C) 1994-2008 Lua.org, PUC-Rio.
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
Fonts
|
||||
---------------
|
||||
|
||||
DejaVu Sans Mono:
|
||||
|
||||
Fonts are (c) Bitstream (see below). DejaVu changes are in public domain.
|
||||
Glyphs imported from Arev fonts are (c) Tavmjong Bah (see below)
|
||||
|
||||
Bitstream Vera Fonts Copyright:
|
||||
|
||||
Copyright (c) 2003 by Bitstream, Inc. All Rights Reserved. Bitstream Vera is
|
||||
a trademark of Bitstream, Inc.
|
||||
|
||||
Arev Fonts Copyright:
|
||||
|
||||
Copyright (c) 2006 by Tavmjong Bah. All Rights Reserved.
|
||||
|
||||
Press Start 2P Font by:
|
||||
|
||||
codeman38 http://www.zone38.net/font/
|
|
@ -0,0 +1,253 @@
|
|||
|
||||
Minetest++
|
||||
|
||||
A game built off of the best free and open source Minecraft clone, Minetest-C55.
|
||||
|
||||
Copyright (c) 2010-2012 Perttu Ahola celeron55@gmail.com and ther contributors (see source file comments and the version control log)
|
||||
|
||||
This contains 2 different game modes, Minetest and Minimal. Game mode Minimal is just a test and will be taken out soon. Game mode Minetest has all the cool features.
|
||||
Further documentation
|
||||
|
||||
Website: http://www.minetest.net
|
||||
Wiki: http://wiki.minetest.com
|
||||
Forum: http://www.minetest.net/forum
|
||||
|
||||
This game is in alpha!
|
||||
|
||||
Don't expect it to work as well as a finished game will.
|
||||
Please tell me about any bugs you come across. Just look in your debug.txt file. (/minetest/bin/debug.txt)
|
||||
But other then that, have fun and expect new features :)
|
||||
|
||||
Default Controls
|
||||
|
||||
WASD: Move
|
||||
Space: Jump
|
||||
E:
|
||||
While walking: Run (need the fast privelage)
|
||||
While flying: Go down
|
||||
Shift: Sneak
|
||||
Q: Drop item
|
||||
R: Open inventory
|
||||
Mouse: Turn/look
|
||||
C: Toggle fly (need fly privelage)
|
||||
X: toggle fast (need fast Privelage)
|
||||
Settable in the configuration file, see the section below.
|
||||
|
||||
Compiling:
|
||||
GNU/Linux
|
||||
Install dependencies.
|
||||
|
||||
Here's an example for Debian/Ubuntu: sudo apt-get install build-essential libirrlicht-dev cmake libbz2-dev libpng12-dev libjpeg8-dev libxxf86vm-dev libgl1-mesa-dev libsqlite3-dev libogg-dev libvorbis-dev libopenal-dev libcurl3
|
||||
Download source:
|
||||
Method 1: Download tarball
|
||||
|
||||
wget https://github.com/jordan4ibanez/minetest/tarball/master -O master.tar.gz
|
||||
tar xf master.tar.gz
|
||||
cd jordan4ibanez-minetest-*
|
||||
|
||||
Method 2: Clone from git
|
||||
|
||||
git clone git://github.com/jordan4ibanez/minetest.git minetestpp
|
||||
cd minetestpp
|
||||
|
||||
Build
|
||||
Method 1: Build a version that runs directly from the source directory
|
||||
|
||||
cmake . -DRUN_IN_PLACE=1
|
||||
make -j2
|
||||
|
||||
Method 2: Build a version that can be installed system-wide
|
||||
|
||||
mkdir build && cd build
|
||||
cmake ..
|
||||
make
|
||||
sudo make install
|
||||
|
||||
Use cmake . -LH to see all CMake options and their current state
|
||||
If you want to install it system-wide (or are making a distribution package), you will want to use -DRUN_IN_PLACE=0
|
||||
You can build a bare server or a bare client by specifying -DBUILD_CLIENT=0 or -DBUILD_SERVER=0
|
||||
You can select between Release and Debug build by -DCMAKE_BUILD_TYPE=
|
||||
Debug build is slower, but gives much more useful output in a debugger
|
||||
|
||||
Windows :
|
||||
|
||||
This section is outdated. In addition to what is described here:
|
||||
In addition to minetest, you need to download minetest_game.
|
||||
If you wish to have sound support, you need libogg, libvorbis and libopenal
|
||||
|
||||
You need:
|
||||
CMake: http://www.cmake.org/cmake/resources/software.html
|
||||
MinGW or Visual Studio http://www.mingw.org/ http://msdn.microsoft.com/en-us/vstudio/default
|
||||
Irrlicht SDK 1.7: http://irrlicht.sourceforge.net/downloads.html
|
||||
Zlib headers (zlib125.zip) http://www.winimage.com/zLibDll/index.html
|
||||
Zlib library (zlibwapi.lib and zlibwapi.dll from zlib125dll.zip): http://www.winimage.com/zLibDll/index.html
|
||||
Optional: gettext bibrary and tools: http://gnuwin32.sourceforge.net/downlinks/gettext.php
|
||||
This is used for other UI languages. Feel free to leave it out.
|
||||
And, of course, Minetest-c55: http://c55.me/minetest/download
|
||||
|
||||
Steps:
|
||||
Select a directory called DIR hereafter in which you will operate.
|
||||
Make sure you have CMake and a compiler installed.
|
||||
Download all the other stuff to DIR and extract them into there. ("extract here", not "extract to packagename/") NOTE: zlib125dll.zip needs to be extracted into zlib125dll
|
||||
All those packages contain a nice base directory in them, which should end up being the direct subdirectories of DIR.
|
||||
You will end up with a directory structure like this:
|
||||
DIR
|
||||
zlib-1.2.5.tar.gz
|
||||
zlib125dll.zip
|
||||
irrlicht-1.7.1.zip
|
||||
110214175330.zip (or whatever, this is the minetest source)
|
||||
zlib-1.2.5
|
||||
zlib.h
|
||||
win32 ...
|
||||
zlib125dll
|
||||
readme.txt
|
||||
dll32 ...
|
||||
irrlicht-1.7.1
|
||||
lib
|
||||
include ...
|
||||
gettext (optional) +bin +include +lib
|
||||
minetest
|
||||
src
|
||||
doc
|
||||
CMakeLists.txt
|
||||
Start up the CMake GUI
|
||||
Select "Browse Source..." and select DIR/minetest
|
||||
Now, if using MSVC:
|
||||
Select "Browse Build..." and select DIR/minetest-build
|
||||
Else if using MinGW:
|
||||
Select "Browse Build..." and select DIR/minetest
|
||||
Select "Configure"
|
||||
Select your compiler
|
||||
It will warn about missing stuff, ignore that at this point. (later don't)
|
||||
Make sure the configuration is as follows (note that the versions may differ for you):
|
||||
|
||||
-----------------
|
||||
BUILD_CLIENT [X]
|
||||
BUILD_SERVER [ ]
|
||||
CMAKE_BUILD_TYPE Release
|
||||
CMAKE_INSTALL_PREFIX DIR/minetest-install
|
||||
IRRLICHT_SOURCE_DIR DIR/irrlicht-1.7.1
|
||||
RUN_IN_PLACE [X]
|
||||
WARN_ALL [ ]
|
||||
ZLIB_DLL DIR/zlib125dll/dll32/zlibwapi.dll
|
||||
ZLIB_INCLUDE_DIR DIR/zlib-1.2.5
|
||||
ZLIB_LIBRARIES DIR/zlib125dll/dll32/zlibwapi.lib
|
||||
GETTEXT_BIN_DIR DIR/gettext/bin
|
||||
GETTEXT_INCLUDE_DIR DIR/gettext/include
|
||||
GETTEXT_LIBRARIES DIR/gettext/lib/intl.lib
|
||||
GETTEXT_MSGFMT DIR/gettext/bin/msgfmt
|
||||
-----------------
|
||||
|
||||
Hit "Configure"
|
||||
Hit "Configure" once again 8)
|
||||
If something is still coloured red, you have a problem.
|
||||
Hit "Generate" If using MSVC:
|
||||
Open the generated minetest.sln
|
||||
The project defaults to the "Debug" configuration. Make very sure to select "Release", unless you want to debug some stuff (it's slower and might not even work at all)
|
||||
Build the ALL_BUILD project
|
||||
Build the INSTALL project
|
||||
You should now have a working game with the executable in DIR/minetest-install/bin/minetest.exe
|
||||
Additionally you may create a zip package by building the PACKAGE project. If using MinGW:
|
||||
Using the command line, browse to the build directory and run 'make' (or mingw32-make or whatever it happens to be)
|
||||
You may need to copy some of the downloaded DLLs into bin/, see what running the produced executable tells you it doesn't have.
|
||||
You should now have a working game with the executable in DIR/minetest/bin/minetest.exe
|
||||
|
||||
This can be automated with a batch script like this
|
||||
|
||||
set sourcedir=%CD%
|
||||
set installpath="C:\tmp\minetest_install"
|
||||
set irrlichtpath="C:\tmp\irrlicht-1.7.2"
|
||||
|
||||
set builddir=%sourcedir%\bvc10
|
||||
mkdir %builddir%
|
||||
pushd %builddir%
|
||||
cmake %sourcedir% -G "Visual Studio 10" -DIRRLICHT_SOURCE_DIR=%irrlichtpath% -DRUN_IN_PLACE=1 -DCMAKE_INSTALL_PREFIX=%installpath%
|
||||
if %errorlevel% neq 0 goto fail
|
||||
"C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\MSBuild.exe" ALL_BUILD.vcxproj /p:Configuration=Release
|
||||
if %errorlevel% neq 0 goto fail
|
||||
"C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\MSBuild.exe" INSTALL.vcxproj /p:Configuration=Release
|
||||
if %errorlevel% neq 0 goto fail
|
||||
"C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\MSBuild.exe" PACKAGE.vcxproj /p:Configuration=Release
|
||||
if %errorlevel% neq 0 goto fail
|
||||
popd
|
||||
echo Finished.
|
||||
exit /b 0
|
||||
|
||||
:fail
|
||||
popd
|
||||
echo Failed.
|
||||
exit /b 1
|
||||
|
||||
License of Minetest-c55 textures and sounds
|
||||
|
||||
This applies to textures and sounds contained in the main Minetest distribution.
|
||||
|
||||
Attribution-ShareAlike 3.0 Unported (CC BY-SA 3.0)
|
||||
http://creativecommons.org/licenses/by-sa/3.0/
|
||||
License of Minetest-c55 source code
|
||||
|
||||
Minetest-c55 Copyright (C) 2010-2011 celeron55, Perttu Ahola celeron55@gmail.com
|
||||
|
||||
This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
Irrlicht
|
||||
|
||||
This program uses the Irrlicht Engine. http://irrlicht.sourceforge.net/
|
||||
|
||||
The Irrlicht Engine License
|
||||
|
||||
Copyright © 2002-2005 Nikolaus Gebhardt
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including commercial applications, and to alter it and redistribute it freely, subject to the following restrictions:
|
||||
|
||||
The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
This notice may not be removed or altered from any source distribution.
|
||||
|
||||
JThread
|
||||
|
||||
This program uses the JThread library. License for JThread follows:
|
||||
|
||||
Copyright (c) 2000-2006 Jori Liesenborgs (jori.liesenborgs@gmail.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
Lua
|
||||
|
||||
Lua is licensed under the terms of the MIT license reproduced below. This means that Lua is free software and can be used for both academic and commercial purposes at absolutely no cost.
|
||||
|
||||
For details and rationale, see http://www.lua.org/license.html .
|
||||
|
||||
Copyright (C) 1994-2008 Lua.org, PUC-Rio.
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
Fonts
|
||||
|
||||
DejaVu Sans Mono:
|
||||
|
||||
Fonts are (c) Bitstream (see below). DejaVu changes are in public domain. Glyphs imported from Arev fonts are (c) Tavmjong Bah (see below)
|
||||
|
||||
Bitstream Vera Fonts Copyright:
|
||||
|
||||
Copyright (c) 2003 by Bitstream, Inc. All Rights Reserved. Bitstream Vera is a trademark of Bitstream, Inc.
|
||||
|
||||
Arev Fonts Copyright:
|
||||
|
||||
Copyright (c) 2006 by Tavmjong Bah. All Rights Reserved.
|
||||
|
||||
Press Start 2P Font by:
|
||||
|
||||
codeman38 http://www.zone38.net/font/
|
||||
|
|
@ -0,0 +1,188 @@
|
|||
-- Minetest: builtin/auth.lua
|
||||
|
||||
--
|
||||
-- Authentication handler
|
||||
--
|
||||
|
||||
function minetest.string_to_privs(str, delim)
|
||||
assert(type(str) == "string")
|
||||
delim = delim or ','
|
||||
privs = {}
|
||||
for _, priv in pairs(string.split(str, delim)) do
|
||||
privs[priv:trim()] = true
|
||||
end
|
||||
return privs
|
||||
end
|
||||
|
||||
function minetest.privs_to_string(privs, delim)
|
||||
assert(type(privs) == "table")
|
||||
delim = delim or ','
|
||||
list = {}
|
||||
for priv, bool in pairs(privs) do
|
||||
if bool then
|
||||
table.insert(list, priv)
|
||||
end
|
||||
end
|
||||
return table.concat(list, delim)
|
||||
end
|
||||
|
||||
assert(minetest.string_to_privs("a,b").b == true)
|
||||
assert(minetest.privs_to_string({a=true,b=true}) == "a,b")
|
||||
|
||||
minetest.auth_file_path = minetest.get_worldpath().."/auth.txt"
|
||||
minetest.auth_table = {}
|
||||
|
||||
local function read_auth_file()
|
||||
local newtable = {}
|
||||
local file, errmsg = io.open(minetest.auth_file_path, 'rb')
|
||||
if not file then
|
||||
minetest.log("info", minetest.auth_file_path.." could not be opened for reading ("..errmsg.."); assuming new world")
|
||||
return
|
||||
end
|
||||
for line in file:lines() do
|
||||
if line ~= "" then
|
||||
local name, password, privilegestring = string.match(line, "([^:]*):([^:]*):([^:]*)")
|
||||
if not name or not password or not privilegestring then
|
||||
error("Invalid line in auth.txt: "..dump(line))
|
||||
end
|
||||
local privileges = minetest.string_to_privs(privilegestring)
|
||||
newtable[name] = {password=password, privileges=privileges}
|
||||
end
|
||||
end
|
||||
io.close(file)
|
||||
minetest.auth_table = newtable
|
||||
minetest.notify_authentication_modified()
|
||||
end
|
||||
|
||||
local function save_auth_file()
|
||||
local newtable = {}
|
||||
-- Check table for validness before attempting to save
|
||||
for name, stuff in pairs(minetest.auth_table) do
|
||||
assert(type(name) == "string")
|
||||
assert(name ~= "")
|
||||
assert(type(stuff) == "table")
|
||||
assert(type(stuff.password) == "string")
|
||||
assert(type(stuff.privileges) == "table")
|
||||
end
|
||||
local file, errmsg = io.open(minetest.auth_file_path, 'w+b')
|
||||
if not file then
|
||||
error(minetest.auth_file_path.." could not be opened for writing: "..errmsg)
|
||||
end
|
||||
for name, stuff in pairs(minetest.auth_table) do
|
||||
local privstring = minetest.privs_to_string(stuff.privileges)
|
||||
file:write(name..":"..stuff.password..":"..privstring..'\n')
|
||||
end
|
||||
io.close(file)
|
||||
end
|
||||
|
||||
read_auth_file()
|
||||
|
||||
minetest.builtin_auth_handler = {
|
||||
get_auth = function(name)
|
||||
assert(type(name) == "string")
|
||||
-- Figure out what password to use for a new player (singleplayer
|
||||
-- always has an empty password, otherwise use default, which is
|
||||
-- usually empty too)
|
||||
local new_password_hash = ""
|
||||
-- If not in authentication table, return nil
|
||||
if not minetest.auth_table[name] then
|
||||
return nil
|
||||
end
|
||||
-- Figure out what privileges the player should have.
|
||||
-- Take a copy of the privilege table
|
||||
local privileges = {}
|
||||
for priv, _ in pairs(minetest.auth_table[name].privileges) do
|
||||
privileges[priv] = true
|
||||
end
|
||||
-- If singleplayer, give all privileges except those marked as give_to_singleplayer = false
|
||||
if minetest.is_singleplayer() then
|
||||
for priv, def in pairs(minetest.registered_privileges) do
|
||||
if def.give_to_singleplayer then
|
||||
privileges[priv] = true
|
||||
end
|
||||
end
|
||||
-- For the admin, give everything
|
||||
elseif name == minetest.setting_get("name") then
|
||||
for priv, def in pairs(minetest.registered_privileges) do
|
||||
privileges[priv] = true
|
||||
end
|
||||
end
|
||||
-- All done
|
||||
return {
|
||||
password = minetest.auth_table[name].password,
|
||||
privileges = privileges,
|
||||
}
|
||||
end,
|
||||
create_auth = function(name, password)
|
||||
assert(type(name) == "string")
|
||||
assert(type(password) == "string")
|
||||
minetest.log('info', "Built-in authentication handler adding player '"..name.."'")
|
||||
minetest.auth_table[name] = {
|
||||
password = password,
|
||||
privileges = minetest.string_to_privs(minetest.setting_get("default_privs")),
|
||||
}
|
||||
save_auth_file()
|
||||
end,
|
||||
set_password = function(name, password)
|
||||
assert(type(name) == "string")
|
||||
assert(type(password) == "string")
|
||||
if not minetest.auth_table[name] then
|
||||
minetest.builtin_auth_handler.create_auth(name, password)
|
||||
else
|
||||
minetest.log('info', "Built-in authentication handler setting password of player '"..name.."'")
|
||||
minetest.auth_table[name].password = password
|
||||
save_auth_file()
|
||||
end
|
||||
return true
|
||||
end,
|
||||
set_privileges = function(name, privileges)
|
||||
assert(type(name) == "string")
|
||||
assert(type(privileges) == "table")
|
||||
if not minetest.auth_table[name] then
|
||||
minetest.builtin_auth_handler.create_auth(name, minetest.get_password_hash(name, minetest.setting_get("default_password")))
|
||||
end
|
||||
minetest.auth_table[name].privileges = privileges
|
||||
minetest.notify_authentication_modified(name)
|
||||
save_auth_file()
|
||||
end,
|
||||
reload = function()
|
||||
read_auth_file()
|
||||
return true
|
||||
end,
|
||||
}
|
||||
|
||||
function minetest.register_authentication_handler(handler)
|
||||
if minetest.registered_auth_handler then
|
||||
error("Add-on authentication handler already registered by "..minetest.registered_auth_handler_modname)
|
||||
end
|
||||
minetest.registered_auth_handler = handler
|
||||
minetest.registered_auth_handler_modname = minetest.get_current_modname()
|
||||
end
|
||||
|
||||
function minetest.get_auth_handler()
|
||||
if minetest.registered_auth_handler then
|
||||
return minetest.registered_auth_handler
|
||||
end
|
||||
return minetest.builtin_auth_handler
|
||||
end
|
||||
|
||||
function minetest.set_player_password(name, password)
|
||||
if minetest.get_auth_handler().set_password then
|
||||
minetest.get_auth_handler().set_password(name, password)
|
||||
end
|
||||
end
|
||||
|
||||
function minetest.set_player_privs(name, privs)
|
||||
if minetest.get_auth_handler().set_privileges then
|
||||
minetest.get_auth_handler().set_privileges(name, privs)
|
||||
end
|
||||
end
|
||||
|
||||
function minetest.auth_reload()
|
||||
if minetest.get_auth_handler().reload then
|
||||
return minetest.get_auth_handler().reload()
|
||||
end
|
||||
return false
|
||||
end
|
||||
|
||||
|
|
@ -0,0 +1,23 @@
|
|||
--
|
||||
-- This file contains built-in stuff in Minetest implemented in Lua.
|
||||
--
|
||||
-- It is always loaded and executed after registration of the C API,
|
||||
-- before loading and running any mods.
|
||||
--
|
||||
|
||||
-- Initialize some very basic things
|
||||
print = minetest.debug
|
||||
math.randomseed(os.time())
|
||||
|
||||
-- Load other files
|
||||
dofile(minetest.get_modpath("__builtin").."/misc_helpers.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/item.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/misc_register.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/item_entity.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/deprecated.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/misc.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/privileges.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/auth.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/chatcommands.lua")
|
||||
dofile(minetest.get_modpath("__builtin").."/static_spawn.lua")
|
||||
|
|
@ -0,0 +1,352 @@
|
|||
-- Minetest: builtin/chatcommands.lua
|
||||
|
||||
--
|
||||
-- Chat command handler
|
||||
--
|
||||
|
||||
minetest.chatcommands = {}
|
||||
function minetest.register_chatcommand(cmd, def)
|
||||
def = def or {}
|
||||
def.params = def.params or ""
|
||||
def.description = def.description or ""
|
||||
def.privs = def.privs or {}
|
||||
minetest.chatcommands[cmd] = def
|
||||
end
|
||||
|
||||
minetest.register_on_chat_message(function(name, message)
|
||||
local cmd, param = string.match(message, "^/([^ ]+) *(.*)")
|
||||
if not param then
|
||||
param = ""
|
||||
end
|
||||
local cmd_def = minetest.chatcommands[cmd]
|
||||
if cmd_def then
|
||||
if not cmd_def.func then
|
||||
-- This is a C++ command
|
||||
return false
|
||||
else
|
||||
local has_privs, missing_privs = minetest.check_player_privs(name, cmd_def.privs)
|
||||
if has_privs then
|
||||
cmd_def.func(name, param)
|
||||
else
|
||||
minetest.chat_send_player(name, "You don't have permission to run this command (missing privileges: "..table.concat(missing_privs, ", ")..")")
|
||||
end
|
||||
return true -- handled chat message
|
||||
end
|
||||
end
|
||||
return false
|
||||
end)
|
||||
|
||||
--
|
||||
-- Chat commands
|
||||
--
|
||||
|
||||
-- Register C++ commands without functions
|
||||
minetest.register_chatcommand("me", {params = nil, description = "chat action (eg. /me orders a pizza)"})
|
||||
minetest.register_chatcommand("status", {description = "print server status line"})
|
||||
minetest.register_chatcommand("shutdown", {params = "", description = "shutdown server", privs = {server=true}})
|
||||
minetest.register_chatcommand("clearobjects", {params = "", description = "clear all objects in world", privs = {server=true}})
|
||||
minetest.register_chatcommand("time", {params = "<0...24000>", description = "set time of day", privs = {settime=true}})
|
||||
minetest.register_chatcommand("ban", {params = "<name>", description = "ban IP of player", privs = {ban=true}})
|
||||
minetest.register_chatcommand("unban", {params = "<name/ip>", description = "remove IP ban", privs = {ban=true}})
|
||||
|
||||
-- Register other commands
|
||||
minetest.register_chatcommand("help", {
|
||||
privs = {},
|
||||
params = "(nothing)/all/privs/<cmd>",
|
||||
description = "Get help for commands or list privileges",
|
||||
func = function(name, param)
|
||||
local format_help_line = function(cmd, def)
|
||||
local msg = "/"..cmd
|
||||
if def.params and def.params ~= "" then msg = msg .. " " .. def.params end
|
||||
if def.description and def.description ~= "" then msg = msg .. ": " .. def.description end
|
||||
return msg
|
||||
end
|
||||
if param == "" then
|
||||
local msg = ""
|
||||
cmds = {}
|
||||
for cmd, def in pairs(minetest.chatcommands) do
|
||||
if minetest.check_player_privs(name, def.privs) then
|
||||
table.insert(cmds, cmd)
|
||||
end
|
||||
end
|
||||
minetest.chat_send_player(name, "Available commands: "..table.concat(cmds, " "))
|
||||
minetest.chat_send_player(name, "Use '/help <cmd>' to get more information, or '/help all' to list everything.")
|
||||
elseif param == "all" then
|
||||
minetest.chat_send_player(name, "Available commands:")
|
||||
for cmd, def in pairs(minetest.chatcommands) do
|
||||
if minetest.check_player_privs(name, def.privs) then
|
||||
minetest.chat_send_player(name, format_help_line(cmd, def))
|
||||
end
|
||||
end
|
||||
elseif param == "privs" then
|
||||
minetest.chat_send_player(name, "Available privileges:")
|
||||
for priv, def in pairs(minetest.registered_privileges) do
|
||||
minetest.chat_send_player(name, priv..": "..def.description)
|
||||
end
|
||||
else
|
||||
local cmd = param
|
||||
def = minetest.chatcommands[cmd]
|
||||
if not def then
|
||||
minetest.chat_send_player(name, "Command not available: "..cmd)
|
||||
else
|
||||
minetest.chat_send_player(name, format_help_line(cmd, def))
|
||||
end
|
||||
end
|
||||
end,
|
||||
})
|
||||
minetest.register_chatcommand("privs", {
|
||||
params = "<name>",
|
||||
description = "print out privileges of player",
|
||||
func = function(name, param)
|
||||
if param == "" then
|
||||
param = name
|
||||
else
|
||||
if not minetest.check_player_privs(name, {privs=true}) then
|
||||
minetest.chat_send_player(name, "Privileges of "..param.." are hidden from you.")
|
||||
end
|
||||
end
|
||||
minetest.chat_send_player(name, "Privileges of "..param..": "..minetest.privs_to_string(minetest.get_player_privs(param), ' '))
|
||||
end,
|
||||
})
|
||||
minetest.register_chatcommand("grant", {
|
||||
params = "<name> <privilege>|all",
|
||||
description = "Give privilege to player",
|
||||
privs = {},
|
||||
func = function(name, param)
|
||||
if not minetest.check_player_privs(name, {privs=true}) and
|
||||
not minetest.check_player_privs(name, {basic_privs=true}) then
|
||||
minetest.chat_send_player(name, "Your privileges are insufficient.")
|
||||
return
|
||||
end
|
||||
local grantname, grantprivstr = string.match(param, "([^ ]+) (.+)")
|
||||
if not grantname or not grantprivstr then
|
||||
minetest.chat_send_player(name, "Invalid parameters (see /help grant)")
|
||||
return
|
||||
end
|
||||
local grantprivs = minetest.string_to_privs(grantprivstr)
|
||||
if grantprivstr == "all" then
|
||||
grantprivs = minetest.registered_privileges
|
||||
end
|
||||
local privs = minetest.get_player_privs(grantname)
|
||||
local privs_known = true
|
||||
for priv, _ in pairs(grantprivs) do
|
||||
if priv ~= "interact" and priv ~= "shout" and priv ~= "interact_extra" and not minetest.check_player_privs(name, {privs=true}) then
|
||||
minetest.chat_send_player(name, "Your privileges are insufficient.")
|
||||
return
|
||||
end
|
||||
if not minetest.registered_privileges[priv] then
|
||||
minetest.chat_send_player(name, "Unknown privilege: "..priv)
|
||||
privs_known = false
|
||||
end
|
||||
privs[priv] = true
|
||||
end
|
||||
if not privs_known then
|
||||
return
|
||||
end
|
||||
minetest.set_player_privs(grantname, privs)
|
||||
minetest.chat_send_player(name, "Privileges of "..grantname..": "..minetest.privs_to_string(minetest.get_player_privs(grantname), ' '))
|
||||
if grantname ~= name then
|
||||
minetest.chat_send_player(grantname, name.." granted you privileges: "..minetest.privs_to_string(grantprivs, ' '))
|
||||
end
|
||||
end,
|
||||
})
|
||||
minetest.register_chatcommand("revoke", {
|
||||
params = "<name> <privilege>|all",
|
||||
description = "Remove privilege from player",
|
||||
privs = {},
|
||||
func = function(name, param)
|
||||
if not minetest.check_player_privs(name, {privs=true}) and
|
||||
not minetest.check_player_privs(name, {basic_privs=true}) then
|
||||
minetest.chat_send_player(name, "Your privileges are insufficient.")
|
||||
return
|
||||
end
|
||||
local revokename, revokeprivstr = string.match(param, "([^ ]+) (.+)")
|
||||
if not revokename or not revokeprivstr then
|
||||
minetest.chat_send_player(name, "Invalid parameters (see /help revoke)")
|
||||
return
|
||||
end
|
||||
local revokeprivs = minetest.string_to_privs(revokeprivstr)
|
||||
local privs = minetest.get_player_privs(revokename)
|
||||
for priv, _ in pairs(revokeprivs) do
|
||||
if priv ~= "interact" and priv ~= "shout" and priv ~= "interact_extra" and not minetest.check_player_privs(name, {privs=true}) then
|
||||
minetest.chat_send_player(name, "Your privileges are insufficient.")
|
||||
return
|
||||
end
|
||||
end
|
||||
if revokeprivstr == "all" then
|
||||
privs = {}
|
||||
else
|
||||
for priv, _ in pairs(revokeprivs) do
|
||||
privs[priv] = nil
|
||||
end
|
||||
end
|
||||
minetest.set_player_privs(revokename, privs)
|
||||
minetest.chat_send_player(name, "Privileges of "..revokename..": "..minetest.privs_to_string(minetest.get_player_privs(revokename), ' '))
|
||||
if revokename ~= name then
|
||||
minetest.chat_send_player(revokename, name.." revoked privileges from you: "..minetest.privs_to_string(revokeprivs, ' '))
|
||||
end
|
||||
end,
|
||||
})
|
||||
minetest.register_chatcommand("setpassword", {
|
||||
params = "<name> <password>",
|
||||
description = "set given password",
|
||||
privs = {password=true},
|
||||
func = function(name, param)
|
||||
if param == "" then
|
||||
minetest.chat_send_player(name, "Password field required")
|
||||
return
|
||||
end
|
||||
minetest.set_player_password(name, param)
|
||||
minetest.chat_send_player(name, "Password set")
|
||||
end,
|
||||
})
|
||||
minetest.register_chatcommand("clearpassword", {
|
||||
params = "<name>",
|
||||
description = "set empty password",
|
||||
privs = {password=true},
|
||||
func = function(name, param)
|
||||
minetest.set_player_password(name, '')
|
||||
minetest.chat_send_player(name, "Password cleared")
|
||||
end,
|
||||
})
|
||||
|
||||
minetest.register_chatcommand("auth_reload", {
|
||||
params = "",
|
||||
description = "reload authentication data",
|
||||
privs = {server=true},
|
||||
func = function(name, param)
|
||||
local done = minetest.auth_reload()
|
||||
if done then
|
||||
minetest.chat_send_player(name, "Done.")
|
||||
else
|
||||
minetest.chat_send_player(name, "Failed.")
|
||||
end
|
||||
end,
|
||||
})
|
||||
|
||||
minetest.register_chatcommand("teleport", {
|
||||
params = "<X>,<Y>,<Z> | <to_name> | <name> <X>,<Y>,<Z> | <name> <to_name>",
|
||||
description = "teleport to given position",
|
||||
privs = {teleport=true},
|
||||
func = function(name, param)
|
||||
-- Returns (pos, true) if found, otherwise (pos, false)
|
||||
local function find_free_position_near(pos)
|
||||
local tries = {
|
||||
{x=1,y=0,z=0},
|
||||
{x=-1,y=0,z=0},
|
||||
{x=0,y=0,z=1},
|
||||
{x=0,y=0,z=-1},
|
||||
}
|
||||
for _, d in ipairs(tries) do
|
||||
local p = {x = pos.x+d.x, y = pos.y+d.y, z = pos.z+d.z}
|
||||
local n = minetest.env:get_node(p)
|
||||
if not minetest.registered_nodes[n.name].walkable then
|
||||
return p, true
|
||||
end
|
||||
end
|
||||
return pos, false
|
||||
end
|
||||
|
||||
local teleportee = nil
|
||||
local p = {}
|
||||
p.x, p.y, p.z = string.match(param, "^([%d.-]+)[, ] *([%d.-]+)[, ] *([%d.-]+)$")
|
||||
teleportee = minetest.env:get_player_by_name(name)
|
||||
if teleportee and p.x and p.y and p.z then
|
||||
minetest.chat_send_player(name, "Teleporting to ("..p.x..", "..p.y..", "..p.z..")")
|
||||
teleportee:setpos(p)
|
||||
return
|
||||
end
|
||||
|
||||
local teleportee = nil
|
||||
local p = nil
|
||||
local target_name = nil
|
||||
target_name = string.match(param, "^([^ ]+)$")
|
||||
teleportee = minetest.env:get_player_by_name(name)
|
||||
if target_name then
|
||||
local target = minetest.env:get_player_by_name(target_name)
|
||||
if target then
|
||||
p = target:getpos()
|
||||
end
|
||||
end
|
||||
if teleportee and p then
|
||||
p = find_free_position_near(p)
|
||||
minetest.chat_send_player(name, "Teleporting to "..target_name.." at ("..p.x..", "..p.y..", "..p.z..")")
|
||||
teleportee:setpos(p)
|
||||
return
|
||||
end
|
||||
|
||||
if minetest.check_player_privs(name, {bring=true}) then
|
||||
local teleportee = nil
|
||||
local p = {}
|
||||
local teleportee_name = nil
|
||||
teleportee_name, p.x, p.y, p.z = string.match(param, "^([^ ]+) +([%d.-]+)[, ] *([%d.-]+)[, ] *([%d.-]+)$")
|
||||
if teleportee_name then
|
||||
teleportee = minetest.env:get_player_by_name(teleportee_name)
|
||||
end
|
||||
if teleportee and p.x and p.y and p.z then
|
||||
minetest.chat_send_player(name, "Teleporting "..teleportee_name.." to ("..p.x..", "..p.y..", "..p.z..")")
|
||||
teleportee:setpos(p)
|
||||
return
|
||||
end
|
||||
|
||||
local teleportee = nil
|
||||
local p = nil
|
||||
local teleportee_name = nil
|
||||
local target_name = nil
|
||||
teleportee_name, target_name = string.match(param, "^([^ ]+) +([^ ]+)$")
|
||||
if teleportee_name then
|
||||
teleportee = minetest.env:get_player_by_name(teleportee_name)
|
||||
end
|
||||
if target_name then
|
||||
local target = minetest.env:get_player_by_name(target_name)
|
||||
if target then
|
||||
p = target:getpos()
|
||||
end
|
||||
end
|
||||
if teleportee and p then
|
||||
p = find_free_position_near(p)
|
||||
minetest.chat_send_player(name, "Teleporting "..teleportee_name.." to "..target_name.." at ("..p.x..", "..p.y..", "..p.z..")")
|
||||
teleportee:setpos(p)
|
||||
return
|
||||
end
|
||||
end
|
||||
|
||||
minetest.chat_send_player(name, "Invalid parameters (\""..param.."\") or player not found (see /help teleport)")
|
||||
return
|
||||
end,
|
||||
})
|
||||
|
||||
minetest.register_chatcommand("set", {
|
||||
params = "[-n] <name> <value> | <name>",
|
||||
description = "set or read server configuration setting",
|
||||
privs = {server=true},
|
||||
func = function(name, param)
|
||||
local arg, setname, setvalue = string.match(param, "(-[n]) ([^ ]+) (.+)")
|
||||
if arg and arg == "-n" and setname and setvalue then
|
||||
minetest.setting_set(setname, setvalue)
|
||||
minetest.chat_send_player(name, setname.." = "..setvalue)
|
||||
return
|
||||
end
|
||||
local setname, setvalue = string.match(param, "([^ ]+) (.+)")
|
||||
if setname and setvalue then
|
||||
if not minetest.setting_get(setname) then
|
||||
minetest.chat_send_player(name, "Failed. Use '/set -n <name> <value>' to create a new setting.")
|
||||
return
|
||||
end
|
||||
minetest.setting_set(setname, setvalue)
|
||||
minetest.chat_send_player(name, setname.." = "..setvalue)
|
||||
return
|
||||
end
|
||||
local setname = string.match(param, "([^ ]+)")
|
||||
if setname then
|
||||
local setvalue = minetest.setting_get(setname)
|
||||
if not setvalue then
|
||||
setvalue = "<not set>"
|
||||
end
|
||||
minetest.chat_send_player(name, setname.." = "..setvalue)
|
||||
return
|
||||
end
|
||||
minetest.chat_send_player(name, "Invalid parameters (see /help set)")
|
||||
end,
|
||||
})
|
||||
|
|
@ -0,0 +1,19 @@
|
|||
-- Minetest: builtin/deprecated.lua
|
||||
|
||||
--
|
||||
-- Default material types
|
||||
--
|
||||
function digprop_err()
|
||||
minetest.log("info", debug.traceback())
|
||||
minetest.log("info", "WARNING: The minetest.digprop_* functions are obsolete and need to be replaced by item groups.")
|
||||
end
|
||||
|
||||
minetest.digprop_constanttime = digprop_err
|
||||
minetest.digprop_stonelike = digprop_err
|
||||
minetest.digprop_dirtlike = digprop_err
|
||||
minetest.digprop_gravellike = digprop_err
|
||||
minetest.digprop_woodlike = digprop_err
|
||||
minetest.digprop_leaveslike = digprop_err
|
||||
minetest.digprop_glasslike = digprop_err
|
||||
|
||||
|
|
@ -0,0 +1,397 @@
|
|||
-- Minetest: builtin/item.lua
|
||||
|
||||
--
|
||||
-- Item definition helpers
|
||||
--
|
||||
|
||||
function minetest.inventorycube(img1, img2, img3)
|
||||
img2 = img2 or img1
|
||||
img3 = img3 or img1
|
||||
return "[inventorycube"
|
||||
.. "{" .. img1:gsub("%^", "&")
|
||||
.. "{" .. img2:gsub("%^", "&")
|
||||
.. "{" .. img3:gsub("%^", "&")
|
||||
end
|
||||
|
||||
function minetest.get_pointed_thing_position(pointed_thing, above)
|
||||
if pointed_thing.type == "node" then
|
||||
if above then
|
||||
-- The position where a node would be placed
|
||||
return pointed_thing.above
|
||||
else
|
||||
-- The position where a node would be dug
|
||||
return pointed_thing.under
|
||||
end
|
||||
elseif pointed_thing.type == "object" then
|
||||
obj = pointed_thing.ref
|
||||
if obj ~= nil then
|
||||
return obj:getpos()
|
||||
else
|
||||
return nil
|
||||
end
|
||||
else
|
||||
return nil
|
||||
end
|
||||
end
|
||||
|
||||
function minetest.dir_to_facedir(dir)
|
||||
if math.abs(dir.x) > math.abs(dir.z) then
|
||||
if dir.x < 0 then
|
||||
return 3
|
||||
else
|
||||
return 1
|
||||
end
|
||||
else
|
||||
if dir.z < 0 then
|
||||
return 2
|
||||
else
|
||||
return 0
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function minetest.dir_to_wallmounted(dir)
|
||||
if math.abs(dir.y) > math.max(math.abs(dir.x), math.abs(dir.z)) then
|
||||
if dir.y < 0 then
|
||||
return 1
|
||||
else
|
||||
return 0
|
||||
end
|
||||
elseif math.abs(dir.x) > math.abs(dir.z) then
|
||||
if dir.x < 0 then
|
||||
return 3
|
||||
else
|
||||
return 2
|
||||
end
|
||||
else
|
||||
if dir.z < 0 then
|
||||
return 5
|
||||
else
|
||||
return 4
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function minetest.get_node_drops(nodename, toolname)
|
||||
local drop = ItemStack({name=nodename}):get_definition().drop
|
||||
if drop == nil then
|
||||
-- default drop
|
||||
return {ItemStack({name=nodename})}
|
||||
elseif type(drop) == "string" then
|
||||
-- itemstring drop
|
||||
return {ItemStack(drop)}
|
||||
elseif drop.items == nil then
|
||||
-- drop = {} to disable default drop
|
||||
return {}
|
||||
end
|
||||
|
||||
-- Extended drop table
|
||||
local got_items = {}
|
||||
local got_count = 0
|
||||
local _, item, tool
|
||||
for _, item in ipairs(drop.items) do
|
||||
local good_rarity = true
|
||||
local good_tool = true
|
||||
if item.rarity ~= nil then
|
||||
good_rarity = item.rarity < 1 or math.random(item.rarity) == 1
|
||||
end
|
||||
if item.tools ~= nil then
|
||||
good_tool = false
|
||||
for _, tool in ipairs(item.tools) do
|
||||
if tool:sub(1, 1) == '~' then
|
||||
good_tool = toolname:find(tool:sub(2)) ~= nil
|
||||
else
|
||||
good_tool = toolname == tool
|
||||
end
|
||||
if good_tool then
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
if good_rarity and good_tool then
|
||||
got_count = got_count + 1
|
||||
for _, add_item in ipairs(item.items) do
|
||||
got_items[#got_items+1] = add_item
|
||||
end
|
||||
if drop.max_items ~= nil and got_count == drop.max_items then
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
return got_items
|
||||
end
|
||||
|
||||
function minetest.item_place_node(itemstack, placer, pointed_thing)
|
||||
local item = itemstack:peek_item()
|
||||
local def = itemstack:get_definition()
|
||||
if def.type == "node" and pointed_thing.type == "node" then
|
||||
local pos = pointed_thing.above
|
||||
local oldnode = minetest.env:get_node(pos)
|
||||
local olddef = ItemStack({name=oldnode.name}):get_definition()
|
||||
|
||||
if not olddef.buildable_to then
|
||||
minetest.log("info", placer:get_player_name() .. " tried to place"
|
||||
.. " node in invalid position " .. minetest.pos_to_string(pos)
|
||||
.. ", replacing " .. oldnode.name)
|
||||
return
|
||||
end
|
||||
|
||||
minetest.log("action", placer:get_player_name() .. " places node "
|
||||
.. def.name .. " at " .. minetest.pos_to_string(pos))
|
||||
|
||||
local newnode = {name = def.name, param1 = 0, param2 = 0}
|
||||
|
||||
-- Calculate direction for wall mounted stuff like torches and signs
|
||||
if def.paramtype2 == 'wallmounted' then
|
||||
local under = pointed_thing.under
|
||||
local above = pointed_thing.above
|
||||
local dir = {x = under.x - above.x, y = under.y - above.y, z = under.z - above.z}
|
||||
newnode.param2 = minetest.dir_to_wallmounted(dir)
|
||||
-- Calculate the direction for furnaces and chests and stuff
|
||||
elseif def.paramtype2 == 'facedir' then
|
||||
local playerpos = placer:getpos()
|
||||
local dir = {x = pos.x - playerpos.x, y = pos.y - playerpos.y, z = pos.z - playerpos.z}
|
||||
newnode.param2 = minetest.dir_to_facedir(dir)
|
||||
minetest.log("action", "facedir: " .. newnode.param2)
|
||||
end
|
||||
|
||||
-- Add node and update
|
||||
minetest.env:add_node(pos, newnode)
|
||||
|
||||
-- Set metadata owner
|
||||
if def.metadata_name ~= "" then
|
||||
minetest.env:get_meta(pos):set_owner(placer:get_player_name())
|
||||
end
|
||||
|
||||
-- Run script hook
|
||||
local _, callback
|
||||
for _, callback in ipairs(minetest.registered_on_placenodes) do
|
||||
callback(pos, newnode, placer)
|
||||
end
|
||||
|
||||
itemstack:take_item()
|
||||
end
|
||||
return itemstack
|
||||
end
|
||||
|
||||
function minetest.item_place_object(itemstack, placer, pointed_thing)
|
||||
local pos = minetest.get_pointed_thing_position(pointed_thing, true)
|
||||
if pos ~= nil then
|
||||
local item = itemstack:take_item()
|
||||
minetest.env:add_item(pos, item)
|
||||
end
|
||||
return itemstack
|
||||
end
|
||||
|
||||
function minetest.item_place(itemstack, placer, pointed_thing)
|
||||
if itemstack:get_definition().type == "node" then
|
||||
return minetest.item_place_node(itemstack, placer, pointed_thing)
|
||||
else
|
||||
return minetest.item_place_object(itemstack, placer, pointed_thing)
|
||||
end
|
||||
end
|
||||
|
||||
function minetest.item_drop(itemstack, dropper, pos)
|
||||
if dropper and dropper:get_player_name() ~= nil then
|
||||
local v = dropper:get_look_dir()
|
||||
local p = {x=pos.x+v.x, y=pos.y+1.5+v.y, z=pos.z+v.z}
|
||||
local obj = minetest.env:add_item(p, itemstack)
|
||||
v.x = v.x*2
|
||||
v.y = v.y*2 + 2
|
||||
v.z = v.z*2
|
||||
obj:setvelocity(v)
|
||||
else
|
||||
minetest.env:add_item(pos, itemstack)
|
||||
end
|
||||
return ""
|
||||
end
|
||||
|
||||
function minetest.item_eat(hp_change, hunger_change, replace_with_item)
|
||||
return function(itemstack, user, pointed_thing) -- closure
|
||||
if itemstack:take_item() ~= nil then
|
||||
user:set_hp(user:get_hp() + hp_change)
|
||||
user:set_hunger(user:get_hunger() + hunger_change)
|
||||
itemstack:add_item(replace_with_item) -- note: replace_with_item is optional
|
||||
end
|
||||
return itemstack
|
||||
end
|
||||
end
|
||||
|
||||
function minetest.node_punch(pos, node, puncher)
|
||||
-- Run script hook
|
||||
local _, callback
|
||||
for _, callback in ipairs(minetest.registered_on_punchnodes) do
|
||||
callback(pos, node, puncher)
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
function minetest.node_dig(pos, node, digger)
|
||||
minetest.debug("node_dig")
|
||||
|
||||
local def = ItemStack({name=node.name}):get_definition()
|
||||
if not def.diggable then
|
||||
minetest.debug("not diggable")
|
||||
minetest.log("info", digger:get_player_name() .. " tried to dig "
|
||||
.. node.name .. " which is not diggable "
|
||||
.. minetest.pos_to_string(pos))
|
||||
return
|
||||
end
|
||||
|
||||
local meta = minetest.env:get_meta(pos)
|
||||
if meta ~= nil and not meta:get_allow_removal() then
|
||||
minetest.debug("dig prevented by metadata")
|
||||
minetest.log("info", digger:get_player_name() .. " tried to dig "
|
||||
.. node.name .. ", but removal is disabled by metadata "
|
||||
.. minetest.pos_to_string(pos))
|
||||
return
|
||||
end
|
||||
|
||||
minetest.log('action', digger:get_player_name() .. " digs "
|
||||
.. node.name .. " at " .. minetest.pos_to_string(pos))
|
||||
|
||||
if not minetest.setting_getbool("creative_mode") then
|
||||
local wielded = digger:get_wielded_item()
|
||||
local drops = minetest.get_node_drops(node.name, wielded:get_name())
|
||||
|
||||
-- Wear out tool
|
||||
tp = wielded:get_tool_capabilities()
|
||||
dp = minetest.get_dig_params(def.groups, tp)
|
||||
wielded:add_wear(dp.wear)
|
||||
digger:set_wielded_item(wielded)
|
||||
|
||||
-- Add dropped items
|
||||
local _, dropped_item
|
||||
for _, dropped_item in ipairs(drops) do
|
||||
minetest.item_drop(dropped_item, nil, pos)
|
||||
end
|
||||
end
|
||||
|
||||
-- Remove node and update
|
||||
minetest.env:remove_node(pos)
|
||||
|
||||
-- Run script hook
|
||||
local _, callback
|
||||
for _, callback in ipairs(minetest.registered_on_dignodes) do
|
||||
callback(pos, node, digger)
|
||||
end
|
||||
end
|
||||
|
||||
-- This is used to allow mods to redefine minetest.item_place and so on
|
||||
local function redef_wrapper(table, name)
|
||||
return function(...)
|
||||
return table[name](...)
|
||||
end
|
||||
end
|
||||
|
||||
--
|
||||
-- Item definition defaults
|
||||
--
|
||||
|
||||
minetest.nodedef_default = {
|
||||
-- Item properties
|
||||
type="node",
|
||||
-- name intentionally not defined here
|
||||
description = "",
|
||||
groups = {},
|
||||
inventory_image = "",
|
||||
wield_image = "",
|
||||
wield_scale = {x=1,y=1,z=1},
|
||||
stack_max = 99,
|
||||
usable = false,
|
||||
liquids_pointable = false,
|
||||
tool_capabilities = nil,
|
||||
|
||||
-- Interaction callbacks
|
||||
on_place = redef_wrapper(minetest, 'item_place'), -- minetest.item_place
|
||||
on_drop = redef_wrapper(minetest, 'item_drop'), -- minetest.item_drop
|
||||
on_use = nil,
|
||||
|
||||
on_punch = redef_wrapper(minetest, 'node_punch'), -- minetest.node_punch
|
||||
on_dig = redef_wrapper(minetest, 'node_dig'), -- minetest.node_dig
|
||||
|
||||
-- Node properties
|
||||
drawtype = "normal",
|
||||
visual_scale = 1.0,
|
||||
tile_images = {""},
|
||||
special_materials = {
|
||||
{image="", backface_culling=true},
|
||||
{image="", backface_culling=true},
|
||||
},
|
||||
alpha = 255,
|
||||
post_effect_color = {a=0, r=0, g=0, b=0},
|
||||
paramtype = "none",
|
||||
paramtype2 = "none",
|
||||
is_ground_content = false,
|
||||
sunlight_propagates = false,
|
||||
walkable = true,
|
||||
pointable = true,
|
||||
diggable = true,
|
||||
climbable = false,
|
||||
buildable_to = false,
|
||||
metadata_name = "",
|
||||
liquidtype = "none",
|
||||
liquid_alternative_flowing = "",
|
||||
liquid_alternative_source = "",
|
||||
liquid_viscosity = 0,
|
||||
light_source = 0,
|
||||
damage_per_second = 0,
|
||||
selection_box = {type="regular"},
|
||||
legacy_facedir_simple = false,
|
||||
legacy_wallmounted = false,
|
||||
}
|
||||
|
||||
minetest.craftitemdef_default = {
|
||||
type="craft",
|
||||
-- name intentionally not defined here
|
||||
description = "",
|
||||
groups = {},
|
||||
inventory_image = "",
|
||||
wield_image = "",
|
||||
wield_scale = {x=1,y=1,z=1},
|
||||
stack_max = 99,
|
||||
liquids_pointable = false,
|
||||
tool_capabilities = nil,
|
||||
|
||||
-- Interaction callbacks
|
||||
on_place = redef_wrapper(minetest, 'item_place'), -- minetest.item_place
|
||||
on_drop = redef_wrapper(minetest, 'item_drop'), -- minetest.item_drop
|
||||
on_use = nil,
|
||||
}
|
||||
|
||||
minetest.tooldef_default = {
|
||||
type="tool",
|
||||
-- name intentionally not defined here
|
||||
description = "",
|
||||
groups = {},
|
||||
inventory_image = "",
|
||||
wield_image = "",
|
||||
wield_scale = {x=1,y=1,z=1},
|
||||
stack_max = 1,
|
||||
liquids_pointable = false,
|
||||
tool_capabilities = nil,
|
||||
|
||||
-- Interaction callbacks
|
||||
on_place = redef_wrapper(minetest, 'item_place'), -- minetest.item_place
|
||||
on_drop = redef_wrapper(minetest, 'item_drop'), -- minetest.item_drop
|
||||
on_use = nil,
|
||||
}
|
||||
|
||||
minetest.noneitemdef_default = { -- This is used for the hand and unknown items
|
||||
type="none",
|
||||
-- name intentionally not defined here
|
||||
description = "",
|
||||
groups = {},
|
||||
inventory_image = "",
|
||||
wield_image = "",
|
||||
wield_scale = {x=1,y=1,z=1},
|
||||
stack_max = 99,
|
||||
liquids_pointable = false,
|
||||
tool_capabilities = nil,
|
||||
|
||||
-- Interaction callbacks
|
||||
on_place = nil,
|
||||
on_drop = nil,
|
||||
on_use = nil,
|
||||
}
|
||||
|
|
@ -0,0 +1,148 @@
|
|||
-- Minetest: builtin/item_entity.lua
|
||||
|
||||
function minetest.spawn_item(pos, item)
|
||||
-- Take item in any format
|
||||
local stack = ItemStack(item)
|
||||
local obj = minetest.env:add_entity(pos, "__builtin:item")
|
||||
obj:get_luaentity():set_item(stack:to_string())
|
||||
return obj
|
||||
end
|
||||
|
||||
minetest.register_entity("__builtin:item", {
|
||||
initial_properties = {
|
||||
hp_max = 1,
|
||||
physical = true,
|
||||
collisionbox = {-0.17,-0.17,-0.17, 0.17,0.17,0.17},
|
||||
visual = "sprite",
|
||||
visual_size = {x=0.5, y=0.5},
|
||||
textures = {""},
|
||||
spritediv = {x=1, y=1},
|
||||
initial_sprite_basepos = {x=0, y=0},
|
||||
is_visible = false,
|
||||
pointable = false,
|
||||
},
|
||||
|
||||
itemstring = '',
|
||||
physical_state = true,
|
||||
dontbugme = true,
|
||||
outercircle = 2.0,
|
||||
innercircle = 0.5,
|
||||
gravity = true,
|
||||
whocaresaboutnodes = false,
|
||||
lastplayer = false,
|
||||
|
||||
set_item = function(self, itemstring)
|
||||
self.itemstring = itemstring
|
||||
local stack = ItemStack(itemstring)
|
||||
local itemtable = stack:to_table()
|
||||
local itemname = nil
|
||||
if itemtable then
|
||||
itemname = stack:to_table().name
|
||||
end
|
||||
local item_texture = nil
|
||||
local item_type = ""
|
||||
if minetest.registered_items[itemname] then
|
||||
item_texture = minetest.registered_items[itemname].inventory_image
|
||||
item_type = minetest.registered_items[itemname].type
|
||||
end
|
||||
prop = {
|
||||
is_visible = true,
|
||||
visual = "sprite",
|
||||
textures = {"unknown_item.png"}
|
||||
}
|
||||
prop.visual = "wielditem"
|
||||
prop.textures = {itemname}
|
||||
prop.visual_size = {x=0.20, y=0.20}
|
||||
prop.automatic_rotate = math.pi * 0.25
|
||||
self.object:set_properties(prop)
|
||||
end,
|
||||
get_staticdata = function(self)
|
||||
return self.itemstring
|
||||
end,
|
||||
|
||||
on_activate = function(self, staticdata)
|
||||
self.itemstring = staticdata
|
||||
self.object:set_armor_groups({immortal=1})
|
||||
self.object:setvelocity({x=math.random(-1.5,1.5), y=0, z=math.random(-1.5,1.5)})
|
||||
self.object:setacceleration({x=0, y=-10, z=0})
|
||||
self:set_item(self.itemstring)
|
||||
end,
|
||||
|
||||
on_step = function(self, dtime)
|
||||
local p = self.object:getpos()
|
||||
p.y = p.y - 0.3
|
||||
local nn = minetest.env:get_node(p).name
|
||||
if minetest.registered_nodes[nn].walkable and self.whocaresaboutnodes == false then
|
||||
if self.physical_state then
|
||||
self.object:setvelocity({x=0, y=0, z=0})
|
||||
self.object:setacceleration({x=0, y=0, z=0})
|
||||
self.physical_state = false
|
||||
self.object:set_properties({
|
||||
physical = false
|
||||
})
|
||||
self.dontbugme = false
|
||||
end
|
||||
else
|
||||
if not self.physical_state and self.gravity == true then
|
||||
self.object:setvelocity({x=0, y=0, z=0})
|
||||
self.object:setacceleration({x=0, y=-10, z=0})
|
||||
self.physical_state = true
|
||||
self.object:set_properties({
|
||||
physical = true
|
||||
})
|
||||
self.dontbugme = true
|
||||
end
|
||||
end
|
||||
local pos = p
|
||||
local objs = minetest.env:get_objects_inside_radius(pos, self.innercircle)
|
||||
local objs2 = minetest.env:get_objects_inside_radius(pos, self.outercircle)
|
||||
for k, obj in pairs(objs) do
|
||||
local objpos=obj:getpos()
|
||||
if objpos.y >= pos.y-1.5 and objpos.y <= pos.y+.5 then
|
||||
if obj:get_player_name() ~= nil then
|
||||
if self.itemstring ~= '' then
|
||||
obj:get_inventory():add_item("main", self.itemstring)
|
||||
soundfile = "pop"
|
||||
minetest.sound_play(soundfile, {gain=0.2})
|
||||
end
|
||||
self.object:remove()
|
||||
end
|
||||
end
|
||||
end
|
||||
local playerfound = false
|
||||
for k, obj in pairs(objs2) do
|
||||
local objpos=obj:getpos()
|
||||
if obj:get_player_name() ~= nil and objpos.y >= pos.y-1.25 and objpos.y <= pos.y+.25 then
|
||||
playerfound = true
|
||||
if self.dontbugme == false then
|
||||
self.lastplayer = true
|
||||
local fx = objpos.x - pos.x
|
||||
local fy = objpos.y - pos.y
|
||||
local fz = objpos.z - pos.z
|
||||
self.gravity = false
|
||||
self.physical_state = false
|
||||
self.object:set_properties({
|
||||
physical = false
|
||||
})
|
||||
self.object:setvelocity({x=fx * 5, y=fy * 5, z=fz * 5})
|
||||
self.dontbugme = true
|
||||
self.whocaresaboutnodes = true
|
||||
end
|
||||
end
|
||||
end
|
||||
if playerfound == false then
|
||||
if self.lastplayer == true then
|
||||
self.lastplayer = false
|
||||
self.object:setvelocity({x=0, y=0, z=0})
|
||||
self.object:setacceleration({x=0, y=-10, z=0})
|
||||
end
|
||||
self.gravity = true
|
||||
self.physical_state = true
|
||||
self.object:set_properties({
|
||||
physical = true
|
||||
})
|
||||
self.whocaresaboutnodes = false
|
||||
end
|
||||
end,
|
||||
})
|
||||
|
|
@ -0,0 +1,101 @@
|
|||
-- Minetest: builtin/misc.lua
|
||||
|
||||
--
|
||||
-- Misc. API functions
|
||||
--
|
||||
|
||||
minetest.timers_to_add = {}
|
||||
minetest.timers = {}
|
||||
minetest.register_globalstep(function(dtime)
|
||||
for _, timer in ipairs(minetest.timers_to_add) do
|
||||
table.insert(minetest.timers, timer)
|
||||
end
|
||||
minetest.timers_to_add = {}
|
||||
for index, timer in ipairs(minetest.timers) do
|
||||
timer.time = timer.time - dtime
|
||||
if timer.time <= 0 then
|
||||
timer.func(timer.param)
|
||||
table.remove(minetest.timers,index)
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
function minetest.after(time, func, param)
|
||||
table.insert(minetest.timers_to_add, {time=time, func=func, param=param})
|
||||
end
|
||||
|
||||
function minetest.check_player_privs(name, privs)
|
||||
local player_privs = minetest.get_player_privs(name)
|
||||
local missing_privileges = {}
|
||||
for priv, val in pairs(privs) do
|
||||
if val then
|
||||
if not player_privs[priv] then
|
||||
table.insert(missing_privileges, priv)
|
||||
end
|
||||
end
|
||||
end
|
||||
if #missing_privileges > 0 then
|
||||
return false, missing_privileges
|
||||
end
|
||||
return true, ""
|
||||
end
|
||||
|
||||
function minetest.get_connected_players()
|
||||
-- This could be optimized a bit, but leave that for later
|
||||
local list = {}
|
||||
for _, obj in pairs(minetest.env:get_objects_inside_radius({x=0,y=0,z=0}, 1000000)) do
|
||||
if obj:get_player_name() then
|
||||
table.insert(list, obj)
|
||||
end
|
||||
end
|
||||
return list
|
||||
end
|
||||
|
||||
function minetest.hash_node_position(pos)
|
||||
return (pos.z+32768)*65536*65536 + (pos.y+32768)*65536 + pos.x+32768
|
||||
end
|
||||
|
||||
function minetest.get_item_group(name, group)
|
||||
if not minetest.registered_items[name] or not
|
||||
minetest.registered_items[name].groups[group] then
|
||||
return 0
|
||||
end
|
||||
return minetest.registered_items[name].groups[group]
|
||||
end
|
||||
|
||||
function minetest.get_node_group(name, group)
|
||||
return minetest.get_item_group(name, group)
|
||||
end
|
||||
|
||||
function minetest.string_to_pos(value)
|
||||
local p = {}
|
||||
p.x, p.y, p.z = string.match(value, "^([%d.-]+)[, ] *([%d.-]+)[, ] *([%d.-]+)$")
|
||||
if p.x and p.y and p.z then
|
||||
p.x = tonumber(p.x)
|
||||
p.y = tonumber(p.y)
|
||||
p.z = tonumber(p.z)
|
||||
return p
|
||||
end
|
||||
local p = {}
|
||||
p.x, p.y, p.z = string.match(value, "^%( *([%d.-]+)[, ] *([%d.-]+)[, ] *([%d.-]+) *%)$")
|
||||
if p.x and p.y and p.z then
|
||||
p.x = tonumber(p.x)
|
||||
p.y = tonumber(p.y)
|
||||
p.z = tonumber(p.z)
|
||||
return p
|
||||
end
|
||||
return nil
|
||||
end
|
||||
|
||||
assert(minetest.string_to_pos("10.0, 5, -2").x == 10)
|
||||
assert(minetest.string_to_pos("( 10.0, 5, -2)").z == -2)
|
||||
assert(minetest.string_to_pos("asd, 5, -2)") == nil)
|
||||
|
||||
function minetest.setting_get_pos(name)
|
||||
local value = minetest.setting_get(name)
|
||||
if not value then
|
||||
return nil
|
||||
end
|
||||
return minetest.string_to_pos(value)
|
||||
end
|
||||
|
|
@ -0,0 +1,94 @@
|
|||
-- Minetest: builtin/misc_helpers.lua
|
||||
|
||||
function basic_dump2(o)
|
||||
if type(o) == "number" then
|
||||
return tostring(o)
|
||||
elseif type(o) == "string" then
|
||||
return string.format("%q", o)
|
||||
elseif type(o) == "boolean" then
|
||||
return tostring(o)
|
||||
elseif type(o) == "function" then
|
||||
return "<function>"
|
||||
elseif type(o) == "userdata" then
|
||||
return "<userdata>"
|
||||
elseif type(o) == "nil" then
|
||||
return "nil"
|
||||
else
|
||||
error("cannot dump a " .. type(o))
|
||||
return nil
|
||||
end
|
||||
end
|
||||
|
||||
function dump2(o, name, dumped)
|
||||
name = name or "_"
|
||||
dumped = dumped or {}
|
||||
io.write(name, " = ")
|
||||
if type(o) == "number" or type(o) == "string" or type(o) == "boolean"
|
||||
or type(o) == "function" or type(o) == "nil"
|
||||
or type(o) == "userdata" then
|
||||
io.write(basic_dump2(o), "\n")
|
||||
elseif type(o) == "table" then
|
||||
if dumped[o] then
|
||||
io.write(dumped[o], "\n")
|
||||
else
|
||||
dumped[o] = name
|
||||
io.write("{}\n") -- new table
|
||||
for k,v in pairs(o) do
|
||||
local fieldname = string.format("%s[%s]", name, basic_dump2(k))
|
||||
dump2(v, fieldname, dumped)
|
||||
end
|
||||
end
|
||||
else
|
||||
error("cannot dump a " .. type(o))
|
||||
return nil
|
||||
end
|
||||
end
|
||||
|
||||
function dump(o, dumped)
|
||||
dumped = dumped or {}
|
||||
if type(o) == "number" then
|
||||
return tostring(o)
|
||||
elseif type(o) == "string" then
|
||||
return string.format("%q", o)
|
||||
elseif type(o) == "table" then
|
||||
if dumped[o] then
|
||||
return "<circular reference>"
|
||||
end
|
||||
dumped[o] = true
|
||||
local t = {}
|
||||
for k,v in pairs(o) do
|
||||
t[#t+1] = "" .. k .. " = " .. dump(v, dumped)
|
||||
end
|
||||
return "{" .. table.concat(t, ", ") .. "}"
|
||||
elseif type(o) == "boolean" then
|
||||
return tostring(o)
|
||||
elseif type(o) == "function" then
|
||||
return "<function>"
|
||||
elseif type(o) == "userdata" then
|
||||
return "<userdata>"
|
||||
elseif type(o) == "nil" then
|
||||
return "nil"
|
||||
else
|
||||
error("cannot dump a " .. type(o))
|
||||
return nil
|
||||
end
|
||||
end
|
||||
|
||||
function string:split(sep)
|
||||
local sep, fields = sep or ",", {}
|
||||
local pattern = string.format("([^%s]+)", sep)
|
||||
self:gsub(pattern, function(c) fields[#fields+1] = c end)
|
||||
return fields
|
||||
end
|
||||
|
||||
function string:trim()
|
||||
return (self:gsub("^%s*(.-)%s*$", "%1"))
|
||||
end
|
||||
|
||||
assert(string.trim("\n \t\tfoo bar\t ") == "foo bar")
|
||||
|
||||
function minetest.pos_to_string(pos)
|
||||
return "(" .. pos.x .. "," .. pos.y .. "," .. pos.z .. ")"
|
||||
end
|
||||
|
||||
|
|
@ -0,0 +1,315 @@
|
|||
-- Minetest: builtin/misc_register.lua
|
||||
|
||||
--
|
||||
-- Make raw registration functions inaccessible to anyone except this file
|
||||
--
|
||||
|
||||
local register_item_raw = minetest.register_item_raw
|
||||
minetest.register_item_raw = nil
|
||||
|
||||
local register_alias_raw = minetest.register_alias_raw
|
||||
minetest.register_item_raw = nil
|
||||
|
||||
--
|
||||
-- Item / entity / ABM registration functions
|
||||
--
|
||||
|
||||
minetest.registered_abms = {}
|
||||
minetest.registered_entities = {}
|
||||
minetest.registered_items = {}
|
||||
minetest.registered_nodes = {}
|
||||
minetest.registered_craftitems = {}
|
||||
minetest.registered_tools = {}
|
||||
minetest.registered_aliases = {}
|
||||
minetest.registered_crafts = {}
|
||||
|
||||
-- For tables that are indexed by item name:
|
||||
-- If table[X] does not exist, default to table[minetest.registered_aliases[X]]
|
||||
local function set_alias_metatable(table)
|
||||
setmetatable(table, {
|
||||
__index = function(name)
|
||||
return rawget(table, minetest.registered_aliases[name])
|
||||
end
|
||||
})
|
||||
end
|
||||
set_alias_metatable(minetest.registered_items)
|
||||
set_alias_metatable(minetest.registered_nodes)
|
||||
set_alias_metatable(minetest.registered_craftitems)
|
||||
set_alias_metatable(minetest.registered_tools)
|
||||
|
||||
-- These item names may not be used because they would interfere
|
||||
-- with legacy itemstrings
|
||||
local forbidden_item_names = {
|
||||
MaterialItem = true,
|
||||
MaterialItem2 = true,
|
||||
MaterialItem3 = true,
|
||||
NodeItem = true,
|
||||
node = true,
|
||||
CraftItem = true,
|
||||
craft = true,
|
||||
MBOItem = true,
|
||||
ToolItem = true,
|
||||
tool = true,
|
||||
}
|
||||
|
||||
local function check_modname_prefix(name)
|
||||
if name:sub(1,1) == ":" then
|
||||
-- Escape the modname prefix enforcement mechanism
|
||||
return name:sub(2)
|
||||
else
|
||||
-- Modname prefix enforcement
|
||||
local expected_prefix = minetest.get_current_modname() .. ":"
|
||||
if name:sub(1, #expected_prefix) ~= expected_prefix then
|
||||
error("Name " .. name .. " does not follow naming conventions: " ..
|
||||
"\"modname:\" or \":\" prefix required")
|
||||
end
|
||||
local subname = name:sub(#expected_prefix+1)
|
||||
if subname:find("[^abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_]") then
|
||||
error("Name " .. name .. " does not follow naming conventions: " ..
|
||||
"contains unallowed characters")
|
||||
end
|
||||
return name
|
||||
end
|
||||
end
|
||||
|
||||
function minetest.register_abm(spec)
|
||||
-- Add to minetest.registered_abms
|
||||
minetest.registered_abms[#minetest.registered_abms+1] = spec
|
||||
end
|
||||
|
||||
function minetest.register_entity(name, prototype)
|
||||
-- Check name
|
||||
if name == nil then
|
||||
error("Unable to register entity: Name is nil")
|
||||
end
|
||||
name = check_modname_prefix(tostring(name))
|
||||
|
||||
prototype.name = name
|
||||
prototype.__index = prototype -- so that it can be used as a metatable
|
||||
|
||||
-- Add to minetest.registered_entities
|
||||
minetest.registered_entities[name] = prototype
|
||||
end
|
||||
|
||||
function minetest.register_item(name, itemdef)
|
||||
-- Check name
|
||||
if name == nil then
|
||||
error("Unable to register item: Name is nil")
|
||||
end
|
||||
name = check_modname_prefix(tostring(name))
|
||||
if forbidden_item_names[name] then
|
||||
error("Unable to register item: Name is forbidden: " .. name)
|
||||
end
|
||||
itemdef.name = name
|
||||
|
||||
-- Apply defaults and add to registered_* table
|
||||
if itemdef.type == "node" then
|
||||
setmetatable(itemdef, {__index = minetest.nodedef_default})
|
||||
minetest.registered_nodes[itemdef.name] = itemdef
|
||||
elseif itemdef.type == "craft" then
|
||||
setmetatable(itemdef, {__index = minetest.craftitemdef_default})
|
||||
minetest.registered_craftitems[itemdef.name] = itemdef
|
||||
elseif itemdef.type == "tool" then
|
||||
setmetatable(itemdef, {__index = minetest.tooldef_default})
|
||||
minetest.registered_tools[itemdef.name] = itemdef
|
||||
elseif itemdef.type == "none" then
|
||||
setmetatable(itemdef, {__index = minetest.noneitemdef_default})
|
||||
else
|
||||
error("Unable to register item: Type is invalid: " .. dump(itemdef))
|
||||
end
|
||||
|
||||
-- Flowing liquid uses param2
|
||||
if itemdef.type == "node" and itemdef.liquidtype == "flowing" then
|
||||
itemdef.paramtype2 = "flowingliquid"
|
||||
end
|
||||
|
||||
-- BEGIN Legacy stuff
|
||||
if itemdef.cookresult_itemstring ~= nil and itemdef.cookresult_itemstring ~= "" then
|
||||
minetest.register_craft({
|
||||
type="cooking",
|
||||
output=itemdef.cookresult_itemstring,
|
||||
recipe=itemdef.name,
|
||||
cooktime=itemdef.furnace_cooktime
|
||||
})
|
||||
end
|
||||
if itemdef.furnace_burntime ~= nil and itemdef.furnace_burntime >= 0 then
|
||||
minetest.register_craft({
|
||||
type="fuel",
|
||||
recipe=itemdef.name,
|
||||
burntime=itemdef.furnace_burntime
|
||||
})
|
||||
end
|
||||
-- END Legacy stuff
|
||||
|
||||
-- Disable all further modifications
|
||||
getmetatable(itemdef).__newindex = {}
|
||||
|
||||
--minetest.log("Registering item: " .. itemdef.name)
|
||||
minetest.registered_items[itemdef.name] = itemdef
|
||||
minetest.registered_aliases[itemdef.name] = nil
|
||||
register_item_raw(itemdef)
|
||||
end
|
||||
|
||||
function minetest.register_node(name, nodedef)
|
||||
nodedef.type = "node"
|
||||
minetest.register_item(name, nodedef)
|
||||
end
|
||||
|
||||
function minetest.register_craftitem(name, craftitemdef)
|
||||
craftitemdef.type = "craft"
|
||||
|
||||
-- BEGIN Legacy stuff
|
||||
if craftitemdef.inventory_image == nil and craftitemdef.image ~= nil then
|
||||
craftitemdef.inventory_image = craftitemdef.image
|
||||
end
|
||||
-- END Legacy stuff
|
||||
|
||||
minetest.register_item(name, craftitemdef)
|
||||
end
|
||||
|
||||
function minetest.register_tool(name, tooldef)
|
||||
tooldef.type = "tool"
|
||||
tooldef.stack_max = 1
|
||||
|
||||
-- BEGIN Legacy stuff
|
||||
if tooldef.inventory_image == nil and tooldef.image ~= nil then
|
||||
tooldef.inventory_image = tooldef.image
|
||||
end
|
||||
if tooldef.tool_capabilities == nil and
|
||||
(tooldef.full_punch_interval ~= nil or
|
||||
tooldef.basetime ~= nil or
|
||||
tooldef.dt_weight ~= nil or
|
||||
tooldef.dt_crackiness ~= nil or
|
||||
tooldef.dt_crumbliness ~= nil or
|
||||
tooldef.dt_cuttability ~= nil or
|
||||
tooldef.basedurability ~= nil or
|
||||
tooldef.dd_weight ~= nil or
|
||||
tooldef.dd_crackiness ~= nil or
|
||||
tooldef.dd_crumbliness ~= nil or
|
||||
tooldef.dd_cuttability ~= nil) then
|
||||
tooldef.tool_capabilities = {
|
||||
full_punch_interval = tooldef.full_punch_interval,
|
||||
basetime = tooldef.basetime,
|
||||
dt_weight = tooldef.dt_weight,
|
||||
dt_crackiness = tooldef.dt_crackiness,
|
||||
dt_crumbliness = tooldef.dt_crumbliness,
|
||||
dt_cuttability = tooldef.dt_cuttability,
|
||||
basedurability = tooldef.basedurability,
|
||||
dd_weight = tooldef.dd_weight,
|
||||
dd_crackiness = tooldef.dd_crackiness,
|
||||
dd_crumbliness = tooldef.dd_crumbliness,
|
||||
dd_cuttability = tooldef.dd_cuttability,
|
||||
}
|
||||
end
|
||||
-- END Legacy stuff
|
||||
|
||||
minetest.register_item(name, tooldef)
|
||||
end
|
||||
|
||||
function minetest.register_alias(name, convert_to)
|
||||
if forbidden_item_names[name] then
|
||||
error("Unable to register alias: Name is forbidden: " .. name)
|
||||
end
|
||||
if minetest.registered_items[name] ~= nil then
|
||||
minetest.log("WARNING: Not registering alias, item with same name" ..
|
||||
" is already defined: " .. name .. " -> " .. convert_to)
|
||||
else
|
||||
--minetest.log("Registering alias: " .. name .. " -> " .. convert_to)
|
||||
minetest.registered_aliases[name] = convert_to
|
||||
register_alias_raw(name, convert_to)
|
||||
end
|
||||
end
|
||||
|
||||
-- Alias the forbidden item names to "" so they can't be
|
||||
-- created via itemstrings (e.g. /give)
|
||||
local name
|
||||
for name in pairs(forbidden_item_names) do
|
||||
minetest.registered_aliases[name] = ""
|
||||
register_alias_raw(name, "")
|
||||
end
|
||||
|
||||
|
||||
-- Deprecated:
|
||||
-- Aliases for minetest.register_alias (how ironic...)
|
||||
--minetest.alias_node = minetest.register_alias
|
||||
--minetest.alias_tool = minetest.register_alias
|
||||
--minetest.alias_craftitem = minetest.register_alias
|
||||
|
||||
--
|
||||
-- Built-in node definitions. Also defined in C.
|
||||
--
|
||||
|
||||
minetest.register_item(":unknown", {
|
||||
type = "none",
|
||||
description = "Unknown Item",
|
||||
inventory_image = "unknown_item.png",
|
||||
on_place = minetest.item_place,
|
||||
on_drop = minetest.item_drop,
|
||||
})
|
||||
|
||||
minetest.register_node(":air", {
|
||||
description = "Air (you hacker you!)",
|
||||
inventory_image = "unknown_block.png",
|
||||
wield_image = "unknown_block.png",
|
||||
drawtype = "airlike",
|
||||
paramtype = "light",
|
||||
sunlight_propagates = true,
|
||||
walkable = false,
|
||||
pointable = false,
|
||||
diggable = false,
|
||||
buildable_to = true,
|
||||
air_equivalent = true,
|
||||
})
|
||||
|
||||
minetest.register_node(":ignore", {
|
||||
description = "Ignore (you hacker you!)",
|
||||
inventory_image = "unknown_block.png",
|
||||
wield_image = "unknown_block.png",
|
||||
drawtype = "airlike",
|
||||
paramtype = "none",
|
||||
sunlight_propagates = false,
|
||||
walkable = false,
|
||||
pointable = false,
|
||||
diggable = false,
|
||||
buildable_to = true, -- A way to remove accidentally placed ignores
|
||||
air_equivalent = true,
|
||||
})
|
||||
|
||||
-- The hand (bare definition)
|
||||
minetest.register_item(":", {
|
||||
type = "none",
|
||||
})
|
||||
|
||||
--
|
||||
-- Creative inventory
|
||||
--
|
||||
|
||||
minetest.creative_inventory = {}
|
||||
|
||||
minetest.add_to_creative_inventory = function(itemstring)
|
||||
table.insert(minetest.creative_inventory, itemstring)
|
||||
end
|
||||
|
||||
--
|
||||
-- Callback registration
|
||||
--
|
||||
|
||||
local function make_registration()
|
||||
local t = {}
|
||||
local registerfunc = function(func) table.insert(t, func) end
|
||||
return t, registerfunc
|
||||
end
|
||||
|
||||
minetest.registered_on_chat_messages, minetest.register_on_chat_message = make_registration()
|
||||
minetest.registered_globalsteps, minetest.register_globalstep = make_registration()
|
||||
minetest.registered_on_placenodes, minetest.register_on_placenode = make_registration()
|
||||
minetest.registered_on_dignodes, minetest.register_on_dignode = make_registration()
|
||||
minetest.registered_on_punchnodes, minetest.register_on_punchnode = make_registration()
|
||||
minetest.registered_on_generateds, minetest.register_on_generated = make_registration()
|
||||
minetest.registered_on_newplayers, minetest.register_on_newplayer = make_registration()
|
||||
minetest.registered_on_dieplayers, minetest.register_on_dieplayer = make_registration()
|
||||
minetest.registered_on_respawnplayers, minetest.register_on_respawnplayer = make_registration()
|
||||
minetest.registered_on_joinplayers, minetest.register_on_joinplayer = make_registration()
|
||||
minetest.registered_on_leaveplayers, minetest.register_on_leaveplayer = make_registration()
|
||||
|
||||
|
|
@ -0,0 +1,48 @@
|
|||
-- Minetest: builtin/privileges.lua
|
||||
|
||||
--
|
||||
-- Privileges
|
||||
--
|
||||
|
||||
minetest.registered_privileges = {}
|
||||
|
||||
function minetest.register_privilege(name, param)
|
||||
local function fill_defaults(def)
|
||||
if def.give_to_singleplayer == nil then
|
||||
def.give_to_singleplayer = true
|
||||
end
|
||||
if def.description == nil then
|
||||
def.description = "(no description)"
|
||||
end
|
||||
end
|
||||
local def = {}
|
||||
if type(param) == "table" then
|
||||
def = param
|
||||
else
|
||||
def = {description = param}
|
||||
end
|
||||
fill_defaults(def)
|
||||
minetest.registered_privileges[name] = def
|
||||
end
|
||||
|
||||
minetest.register_privilege("interact", "Can interact with things and modify the world")
|
||||
minetest.register_privilege("teleport", "Can use /teleport command")
|
||||
minetest.register_privilege("bring", "Can teleport other players")
|
||||
minetest.register_privilege("settime", "Can use /time")
|
||||
minetest.register_privilege("privs", "Can modify privileges")
|
||||
minetest.register_privilege("basic_privs", "Can modify 'shout' and 'interact' privileges")
|
||||
minetest.register_privilege("server", "Can do server maintenance stuff")
|
||||
minetest.register_privilege("shout", "Can speak in chat")
|
||||
minetest.register_privilege("ban", "Can ban and unban players")
|
||||
minetest.register_privilege("give", "Can use /give and /giveme")
|
||||
minetest.register_privilege("password", "Can use /setpassword and /clearpassword")
|
||||
minetest.register_privilege("fly", {
|
||||
description = "Can fly using the free_move mode",
|
||||
give_to_singleplayer = false,
|
||||
})
|
||||
minetest.register_privilege("fast", {
|
||||
description = "Can walk fast using the fast_move mode",
|
||||
give_to_singleplayer = false,
|
||||
})
|
||||
|
||||
|
|
@ -0,0 +1,33 @@
|
|||
-- Minetest: builtin/static_spawn.lua
|
||||
|
||||
local function warn_invalid_static_spawnpoint()
|
||||
if minetest.setting_get("static_spawnpoint") and
|
||||
not minetest.setting_get_pos("static_spawnpoint") then
|
||||
minetest.log('error', "The static_spawnpoint setting is invalid: \""..
|
||||
minetest.setting_get("static_spawnpoint").."\"")
|
||||
end
|
||||
end
|
||||
|
||||
warn_invalid_static_spawnpoint()
|
||||
|
||||
local function put_player_in_spawn(obj)
|
||||
warn_invalid_static_spawnpoint()
|
||||
local static_spawnpoint = minetest.setting_get_pos("static_spawnpoint")
|
||||
if not static_spawnpoint then
|
||||
return false
|
||||
end
|
||||
minetest.log('action', "Moving "..obj:get_player_name()..
|
||||
" to static spawnpoint at "..
|
||||
minetest.pos_to_string(static_spawnpoint))
|
||||
obj:setpos(static_spawnpoint)
|
||||
return true
|
||||
end
|
||||
|
||||
minetest.register_on_newplayer(function(obj)
|
||||
put_player_in_spawn(obj)
|
||||
end)
|
||||
|
||||
minetest.register_on_respawnplayer(function(obj)
|
||||
return put_player_in_spawn(obj)
|
||||
end)
|
||||
|
|
@ -0,0 +1,32 @@
|
|||
# - Find CURL
|
||||
# Find the native CURL includes and libraries
|
||||
#
|
||||
# CURL_INCLUDE_DIR - where to find vorbis.h, etc.
|
||||
# CURL_LIBRARIES - List of libraries when using vorbis(file).
|
||||
# CURL_FOUND - True if vorbis found.
|
||||
|
||||
if(NOT GP2XWIZ)
|
||||
if(CURL_INCLUDE_DIR)
|
||||
# Already in cache, be silent
|
||||
set(CURL_FIND_QUIETLY TRUE)
|
||||
endif(CURL_INCLUDE_DIR)
|
||||
find_library(CURL_LIBRARY NAMES curl)
|
||||
# Handle the QUIETLY and REQUIRED arguments and set VORBIS_FOUND
|
||||
# to TRUE if all listed variables are TRUE.
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(CURL DEFAULT_MSG CURL_INCLUDE_DIR CURL_LIBRARY)
|
||||
else(NOT GP2XWIZ)
|
||||
find_package_handle_standard_args(VORBIS DEFAULT_MSG
|
||||
CURL_INCLUDE_DIR CURL_LIBRARY)
|
||||
endif(NOT GP2XWIZ)
|
||||
|
||||
if(CURL_FOUND)
|
||||
if(NOT GP2XWIZ)
|
||||
set(CURL_LIBRARY ${CURL_LIBRARY})
|
||||
else(NOT GP2XWIZ)
|
||||
set(CURL_LIBRARY ${CURL_LIBRARY})
|
||||
endif(NOT GP2XWIZ)
|
||||
else(CURL_FOUND)
|
||||
set(CURL_LIBRARY)
|
||||
endif(CURL_FOUND)
|
||||
|
|
@ -0,0 +1,72 @@
|
|||
# Package finder for gettext libs and include files
|
||||
|
||||
SET(CUSTOM_GETTEXT_PATH "${PROJECT_SOURCE_DIR}/../../gettext"
|
||||
CACHE FILEPATH "path to custom gettext")
|
||||
|
||||
# by default
|
||||
SET(GETTEXT_FOUND FALSE)
|
||||
|
||||
FIND_PATH(GETTEXT_INCLUDE_DIR
|
||||
NAMES libintl.h
|
||||
PATHS "${CUSTOM_GETTEXT_PATH}/include"
|
||||
DOC "gettext include directory")
|
||||
|
||||
FIND_PROGRAM(GETTEXT_MSGFMT
|
||||
NAMES msgfmt
|
||||
PATHS "${CUSTOM_GETTEXT_PATH}/bin"
|
||||
DOC "path to msgfmt")
|
||||
|
||||
# modern Linux, as well as Mac, seem to not need require special linking
|
||||
# they do not because gettext is part of glibc
|
||||
# TODO check the requirements on other BSDs and older Linux
|
||||
IF (WIN32)
|
||||
IF(MSVC)
|
||||
SET(GETTEXT_LIB_NAMES
|
||||
libintl.lib intl.lib libintl3.lib intl3.lib)
|
||||
ELSE()
|
||||
SET(GETTEXT_LIB_NAMES
|
||||
libintl.dll.a intl.dll.a libintl3.dll.a intl3.dll.a)
|
||||
ENDIF()
|
||||
FIND_LIBRARY(GETTEXT_LIBRARY
|
||||
NAMES ${GETTEXT_LIB_NAMES}
|
||||
PATHS "${CUSTOM_GETTEXT_PATH}/lib"
|
||||
DOC "gettext *intl*.lib")
|
||||
FIND_FILE(GETTEXT_DLL
|
||||
NAMES libintl.dll intl.dll libintl3.dll intl3.dll
|
||||
PATHS "${CUSTOM_GETTEXT_PATH}/bin" "${CUSTOM_GETTEXT_PATH}/lib"
|
||||
DOC "gettext *intl*.dll")
|
||||
FIND_FILE(GETTEXT_ICONV_DLL
|
||||
NAMES libiconv2.dll
|
||||
PATHS "${CUSTOM_GETTEXT_PATH}/bin" "${CUSTOM_GETTEXT_PATH}/lib"
|
||||
DOC "gettext *iconv*.lib")
|
||||
ENDIF(WIN32)
|
||||
|
||||
IF(GETTEXT_INCLUDE_DIR AND GETTEXT_MSGFMT)
|
||||
IF (WIN32)
|
||||
# in the Win32 case check also for the extra linking requirements
|
||||
IF(GETTEXT_LIBRARY AND GETTEXT_DLL AND GETTEXT_ICONV_DLL)
|
||||
SET(GETTEXT_FOUND TRUE)
|
||||
ENDIF()
|
||||
ELSE(WIN32)
|
||||
# *BSD variants require special linkage as they don't use glibc
|
||||
IF(${CMAKE_SYSTEM_NAME} MATCHES "BSD")
|
||||
SET(GETTEXT_LIBRARY "intl")
|
||||
ENDIF(${CMAKE_SYSTEM_NAME} MATCHES "BSD")
|
||||
SET(GETTEXT_FOUND TRUE)
|
||||
ENDIF(WIN32)
|
||||
ENDIF()
|
||||
|
||||
IF(GETTEXT_FOUND)
|
||||
SET(GETTEXT_PO_PATH ${CMAKE_SOURCE_DIR}/po)
|
||||
SET(GETTEXT_MO_BUILD_PATH ${CMAKE_BINARY_DIR}/locale/<locale>/LC_MESSAGES)
|
||||
SET(GETTEXT_MO_DEST_PATH ${LOCALEDIR}/<locale>/LC_MESSAGES)
|
||||
FILE(GLOB GETTEXT_AVAILABLE_LOCALES RELATIVE ${GETTEXT_PO_PATH} "${GETTEXT_PO_PATH}/*")
|
||||
LIST(REMOVE_ITEM GETTEXT_AVAILABLE_LOCALES minetest.pot)
|
||||
MACRO(SET_MO_PATHS _buildvar _destvar _locale)
|
||||
STRING(REPLACE "<locale>" ${_locale} ${_buildvar} ${GETTEXT_MO_BUILD_PATH})
|
||||
STRING(REPLACE "<locale>" ${_locale} ${_destvar} ${GETTEXT_MO_DEST_PATH})
|
||||
ENDMACRO(SET_MO_PATHS)
|
||||
ELSE()
|
||||
SET(GETTEXT_INCLUDE_DIR "")
|
||||
SET(GETTEXT_LIBRARY "")
|
||||
ENDIF()
|
|
@ -0,0 +1,94 @@
|
|||
#FindIrrlicht.cmake
|
||||
|
||||
set(IRRLICHT_SOURCE_DIR "" CACHE PATH "Path to irrlicht source directory (optional)")
|
||||
|
||||
if( UNIX )
|
||||
# Unix
|
||||
else( UNIX )
|
||||
# Windows
|
||||
endif( UNIX )
|
||||
|
||||
# Find include directory
|
||||
|
||||
if(NOT IRRLICHT_SOURCE_DIR STREQUAL "")
|
||||
set(IRRLICHT_SOURCE_DIR_INCLUDE
|
||||
"${IRRLICHT_SOURCE_DIR}/include"
|
||||
)
|
||||
|
||||
set(IRRLICHT_LIBRARY_NAMES libIrrlicht.a Irrlicht Irrlicht.lib)
|
||||
|
||||
if(WIN32)
|
||||
if(MSVC)
|
||||
set(IRRLICHT_SOURCE_DIR_LIBS "${IRRLICHT_SOURCE_DIR}/lib/Win32-visualstudio")
|
||||
set(IRRLICHT_LIBRARY_NAMES Irrlicht.lib)
|
||||
else()
|
||||
set(IRRLICHT_SOURCE_DIR_LIBS "${IRRLICHT_SOURCE_DIR}/lib/Win32-gcc")
|
||||
set(IRRLICHT_LIBRARY_NAMES libIrrlicht.a libIrrlicht.dll.a)
|
||||
endif()
|
||||
else()
|
||||
set(IRRLICHT_SOURCE_DIR_LIBS "${IRRLICHT_SOURCE_DIR}/lib/Linux")
|
||||
set(IRRLICHT_LIBRARY_NAMES libIrrlicht.a)
|
||||
endif()
|
||||
|
||||
FIND_PATH(IRRLICHT_INCLUDE_DIR NAMES irrlicht.h
|
||||
PATHS
|
||||
${IRRLICHT_SOURCE_DIR_INCLUDE}
|
||||
NO_DEFAULT_PATH
|
||||
)
|
||||
|
||||
FIND_LIBRARY(IRRLICHT_LIBRARY NAMES ${IRRLICHT_LIBRARY_NAMES}
|
||||
PATHS
|
||||
${IRRLICHT_SOURCE_DIR_LIBS}
|
||||
NO_DEFAULT_PATH
|
||||
)
|
||||
|
||||
else()
|
||||
|
||||
FIND_PATH(IRRLICHT_INCLUDE_DIR NAMES irrlicht.h
|
||||
PATHS
|
||||
/usr/local/include/irrlicht
|
||||
/usr/include/irrlicht
|
||||
)
|
||||
|
||||
FIND_LIBRARY(IRRLICHT_LIBRARY NAMES libIrrlicht.a Irrlicht
|
||||
PATHS
|
||||
/usr/local/lib
|
||||
/usr/lib
|
||||
)
|
||||
endif()
|
||||
|
||||
MESSAGE(STATUS "IRRLICHT_SOURCE_DIR = ${IRRLICHT_SOURCE_DIR}")
|
||||
MESSAGE(STATUS "IRRLICHT_INCLUDE_DIR = ${IRRLICHT_INCLUDE_DIR}")
|
||||
MESSAGE(STATUS "IRRLICHT_LIBRARY = ${IRRLICHT_LIBRARY}")
|
||||
|
||||
# On windows, find the dll for installation
|
||||
if(WIN32)
|
||||
if(MSVC)
|
||||
FIND_FILE(IRRLICHT_DLL NAMES Irrlicht.dll
|
||||
PATHS
|
||||
"${IRRLICHT_SOURCE_DIR}/bin/Win32-VisualStudio"
|
||||
DOC "Path of the Irrlicht dll (for installation)"
|
||||
)
|
||||
else()
|
||||
FIND_FILE(IRRLICHT_DLL NAMES Irrlicht.dll
|
||||
PATHS
|
||||
"${IRRLICHT_SOURCE_DIR}/bin/Win32-gcc"
|
||||
DOC "Path of the Irrlicht dll (for installation)"
|
||||
)
|
||||
endif()
|
||||
MESSAGE(STATUS "IRRLICHT_DLL = ${IRRLICHT_DLL}")
|
||||
endif(WIN32)
|
||||
|
||||
# handle the QUIETLY and REQUIRED arguments and set IRRLICHT_FOUND to TRUE if
|
||||
# all listed variables are TRUE
|
||||
INCLUDE(FindPackageHandleStandardArgs)
|
||||
FIND_PACKAGE_HANDLE_STANDARD_ARGS(IRRLICHT DEFAULT_MSG IRRLICHT_LIBRARY IRRLICHT_INCLUDE_DIR)
|
||||
|
||||
IF(IRRLICHT_FOUND)
|
||||
SET(IRRLICHT_LIBRARIES ${IRRLICHT_LIBRARY})
|
||||
ELSE(IRRLICHT_FOUND)
|
||||
SET(IRRLICHT_LIBRARIES)
|
||||
ENDIF(IRRLICHT_FOUND)
|
||||
|
||||
MARK_AS_ADVANCED(IRRLICHT_LIBRARY IRRLICHT_INCLUDE_DIR IRRLICHT_DLL)
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
# Look for jthread, use our own if not found
|
||||
|
||||
FIND_PATH(JTHREAD_INCLUDE_DIR jthread.h)
|
||||
|
||||
FIND_LIBRARY(JTHREAD_LIBRARY NAMES jthread)
|
||||
|
||||
IF(JTHREAD_LIBRARY AND JTHREAD_INCLUDE_DIR)
|
||||
SET( JTHREAD_FOUND TRUE )
|
||||
ENDIF(JTHREAD_LIBRARY AND JTHREAD_INCLUDE_DIR)
|
||||
|
||||
IF(JTHREAD_FOUND)
|
||||
MESSAGE(STATUS "Found system jthread header file in ${JTHREAD_INCLUDE_DIR}")
|
||||
MESSAGE(STATUS "Found system jthread library ${JTHREAD_LIBRARY}")
|
||||
ELSE(JTHREAD_FOUND)
|
||||
SET(JTHREAD_INCLUDE_DIR ${PROJECT_SOURCE_DIR}/jthread)
|
||||
SET(JTHREAD_LIBRARY jthread)
|
||||
MESSAGE(STATUS "Using project jthread library")
|
||||
ENDIF(JTHREAD_FOUND)
|
|
@ -0,0 +1,18 @@
|
|||
# Look for sqlite3, use our own if not found
|
||||
|
||||
FIND_PATH(SQLITE3_INCLUDE_DIR sqlite3.h)
|
||||
|
||||
FIND_LIBRARY(SQLITE3_LIBRARY NAMES sqlite3)
|
||||
|
||||
IF(SQLITE3_LIBRARY AND SQLITE3_INCLUDE_DIR)
|
||||
SET( SQLITE3_FOUND TRUE )
|
||||
ENDIF(SQLITE3_LIBRARY AND SQLITE3_INCLUDE_DIR)
|
||||
|
||||
IF(SQLITE3_FOUND)
|
||||
MESSAGE(STATUS "Found system sqlite3 header file in ${SQLITE3_INCLUDE_DIR}")
|
||||
MESSAGE(STATUS "Found system sqlite3 library ${SQLITE3_LIBRARY}")
|
||||
ELSE(SQLITE3_FOUND)
|
||||
SET(SQLITE3_INCLUDE_DIR ${PROJECT_SOURCE_DIR}/sqlite)
|
||||
SET(SQLITE3_LIBRARY sqlite3)
|
||||
MESSAGE(STATUS "Using project sqlite3 library")
|
||||
ENDIF(SQLITE3_FOUND)
|
|
@ -0,0 +1,46 @@
|
|||
# - Find vorbis
|
||||
# Find the native vorbis includes and libraries
|
||||
#
|
||||
# VORBIS_INCLUDE_DIR - where to find vorbis.h, etc.
|
||||
# OGG_INCLUDE_DIR - where to find ogg/ogg.h, etc.
|
||||
# VORBIS_LIBRARIES - List of libraries when using vorbis(file).
|
||||
# VORBIS_FOUND - True if vorbis found.
|
||||
|
||||
if(NOT GP2XWIZ)
|
||||
if(VORBIS_INCLUDE_DIR)
|
||||
# Already in cache, be silent
|
||||
set(VORBIS_FIND_QUIETLY TRUE)
|
||||
endif(VORBIS_INCLUDE_DIR)
|
||||
find_path(OGG_INCLUDE_DIR ogg/ogg.h)
|
||||
find_path(VORBIS_INCLUDE_DIR vorbis/vorbisfile.h)
|
||||
# MSVC built ogg/vorbis may be named ogg_static and vorbis_static
|
||||
find_library(OGG_LIBRARY NAMES ogg ogg_static)
|
||||
find_library(VORBIS_LIBRARY NAMES vorbis vorbis_static)
|
||||
find_library(VORBISFILE_LIBRARY NAMES vorbisfile vorbisfile_static)
|
||||
# Handle the QUIETLY and REQUIRED arguments and set VORBIS_FOUND
|
||||
# to TRUE if all listed variables are TRUE.
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(VORBIS DEFAULT_MSG
|
||||
OGG_INCLUDE_DIR VORBIS_INCLUDE_DIR
|
||||
OGG_LIBRARY VORBIS_LIBRARY VORBISFILE_LIBRARY)
|
||||
else(NOT GP2XWIZ)
|
||||
find_path(VORBIS_INCLUDE_DIR tremor/ivorbisfile.h)
|
||||
find_library(VORBIS_LIBRARY NAMES vorbis_dec)
|
||||
find_package_handle_standard_args(VORBIS DEFAULT_MSG
|
||||
VORBIS_INCLUDE_DIR VORBIS_LIBRARY)
|
||||
endif(NOT GP2XWIZ)
|
||||
|
||||
if(VORBIS_FOUND)
|
||||
if(NOT GP2XWIZ)
|
||||
set(VORBIS_LIBRARIES ${VORBISFILE_LIBRARY} ${VORBIS_LIBRARY}
|
||||
${OGG_LIBRARY})
|
||||
else(NOT GP2XWIZ)
|
||||
set(VORBIS_LIBRARIES ${VORBIS_LIBRARY})
|
||||
endif(NOT GP2XWIZ)
|
||||
else(VORBIS_FOUND)
|
||||
set(VORBIS_LIBRARIES)
|
||||
endif(VORBIS_FOUND)
|
||||
|
||||
mark_as_advanced(OGG_INCLUDE_DIR VORBIS_INCLUDE_DIR)
|
||||
mark_as_advanced(OGG_LIBRARY VORBIS_LIBRARY VORBISFILE_LIBRARY)
|
||||
|
|
@ -0,0 +1,21 @@
|
|||
#
|
||||
# Random macros
|
||||
#
|
||||
|
||||
# Not used ATM
|
||||
|
||||
MACRO (GETDATETIME RESULT)
|
||||
IF (WIN32)
|
||||
EXECUTE_PROCESS(COMMAND "cmd" /C echo %date% %time% OUTPUT_VARIABLE ${RESULT})
|
||||
string(REGEX REPLACE "\n" "" ${RESULT} "${${RESULT}}")
|
||||
ELSEIF(UNIX)
|
||||
EXECUTE_PROCESS(COMMAND "date" "+%Y-%m-%d_%H:%M:%S" OUTPUT_VARIABLE ${RESULT})
|
||||
string(REGEX REPLACE "\n" "" ${RESULT} "${${RESULT}}")
|
||||
ELSE (WIN32)
|
||||
MESSAGE(SEND_ERROR "date not implemented")
|
||||
SET(${RESULT} "Unknown")
|
||||
ENDIF (WIN32)
|
||||
|
||||
string(REGEX REPLACE " " "_" ${RESULT} "${${RESULT}}")
|
||||
ENDMACRO (GETDATETIME)
|
||||
|
|
@ -0,0 +1,339 @@
|
|||
GNU GENERAL PUBLIC LICENSE
|
||||
Version 2, June 1991
|
||||
|
||||
Copyright (C) 1989, 1991 Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
Everyone is permitted to copy and distribute verbatim copies
|
||||
of this license document, but changing it is not allowed.
|
||||
|
||||
Preamble
|
||||
|
||||
The licenses for most software are designed to take away your
|
||||
freedom to share and change it. By contrast, the GNU General Public
|
||||
License is intended to guarantee your freedom to share and change free
|
||||
software--to make sure the software is free for all its users. This
|
||||
General Public License applies to most of the Free Software
|
||||
Foundation's software and to any other program whose authors commit to
|
||||
using it. (Some other Free Software Foundation software is covered by
|
||||
the GNU Lesser General Public License instead.) You can apply it to
|
||||
your programs, too.
|
||||
|
||||
When we speak of free software, we are referring to freedom, not
|
||||
price. Our General Public Licenses are designed to make sure that you
|
||||
have the freedom to distribute copies of free software (and charge for
|
||||
this service if you wish), that you receive source code or can get it
|
||||
if you want it, that you can change the software or use pieces of it
|
||||
in new free programs; and that you know you can do these things.
|
||||
|
||||
To protect your rights, we need to make restrictions that forbid
|
||||
anyone to deny you these rights or to ask you to surrender the rights.
|
||||
These restrictions translate to certain responsibilities for you if you
|
||||
distribute copies of the software, or if you modify it.
|
||||
|
||||
For example, if you distribute copies of such a program, whether
|
||||
gratis or for a fee, you must give the recipients all the rights that
|
||||
you have. You must make sure that they, too, receive or can get the
|
||||
source code. And you must show them these terms so they know their
|
||||
rights.
|
||||
|
||||
We protect your rights with two steps: (1) copyright the software, and
|
||||
(2) offer you this license which gives you legal permission to copy,
|
||||
distribute and/or modify the software.
|
||||
|
||||
Also, for each author's protection and ours, we want to make certain
|
||||
that everyone understands that there is no warranty for this free
|
||||
software. If the software is modified by someone else and passed on, we
|
||||
want its recipients to know that what they have is not the original, so
|
||||
that any problems introduced by others will not reflect on the original
|
||||
authors' reputations.
|
||||
|
||||
Finally, any free program is threatened constantly by software
|
||||
patents. We wish to avoid the danger that redistributors of a free
|
||||
program will individually obtain patent licenses, in effect making the
|
||||
program proprietary. To prevent this, we have made it clear that any
|
||||
patent must be licensed for everyone's free use or not licensed at all.
|
||||
|
||||
The precise terms and conditions for copying, distribution and
|
||||
modification follow.
|
||||
|
||||
GNU GENERAL PUBLIC LICENSE
|
||||
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
||||
|
||||
0. This License applies to any program or other work which contains
|
||||
a notice placed by the copyright holder saying it may be distributed
|
||||
under the terms of this General Public License. The "Program", below,
|
||||
refers to any such program or work, and a "work based on the Program"
|
||||
means either the Program or any derivative work under copyright law:
|
||||
that is to say, a work containing the Program or a portion of it,
|
||||
either verbatim or with modifications and/or translated into another
|
||||
language. (Hereinafter, translation is included without limitation in
|
||||
the term "modification".) Each licensee is addressed as "you".
|
||||
|
||||
Activities other than copying, distribution and modification are not
|
||||
covered by this License; they are outside its scope. The act of
|
||||
running the Program is not restricted, and the output from the Program
|
||||
is covered only if its contents constitute a work based on the
|
||||
Program (independent of having been made by running the Program).
|
||||
Whether that is true depends on what the Program does.
|
||||
|
||||
1. You may copy and distribute verbatim copies of the Program's
|
||||
source code as you receive it, in any medium, provided that you
|
||||
conspicuously and appropriately publish on each copy an appropriate
|
||||
copyright notice and disclaimer of warranty; keep intact all the
|
||||
notices that refer to this License and to the absence of any warranty;
|
||||
and give any other recipients of the Program a copy of this License
|
||||
along with the Program.
|
||||
|
||||
You may charge a fee for the physical act of transferring a copy, and
|
||||
you may at your option offer warranty protection in exchange for a fee.
|
||||
|
||||
2. You may modify your copy or copies of the Program or any portion
|
||||
of it, thus forming a work based on the Program, and copy and
|
||||
distribute such modifications or work under the terms of Section 1
|
||||
above, provided that you also meet all of these conditions:
|
||||
|
||||
a) You must cause the modified files to carry prominent notices
|
||||
stating that you changed the files and the date of any change.
|
||||
|
||||
b) You must cause any work that you distribute or publish, that in
|
||||
whole or in part contains or is derived from the Program or any
|
||||
part thereof, to be licensed as a whole at no charge to all third
|
||||
parties under the terms of this License.
|
||||
|
||||
c) If the modified program normally reads commands interactively
|
||||
when run, you must cause it, when started running for such
|
||||
interactive use in the most ordinary way, to print or display an
|
||||
announcement including an appropriate copyright notice and a
|
||||
notice that there is no warranty (or else, saying that you provide
|
||||
a warranty) and that users may redistribute the program under
|
||||
these conditions, and telling the user how to view a copy of this
|
||||
License. (Exception: if the Program itself is interactive but
|
||||
does not normally print such an announcement, your work based on
|
||||
the Program is not required to print an announcement.)
|
||||
|
||||
These requirements apply to the modified work as a whole. If
|
||||
identifiable sections of that work are not derived from the Program,
|
||||
and can be reasonably considered independent and separate works in
|
||||
themselves, then this License, and its terms, do not apply to those
|
||||
sections when you distribute them as separate works. But when you
|
||||
distribute the same sections as part of a whole which is a work based
|
||||
on the Program, the distribution of the whole must be on the terms of
|
||||
this License, whose permissions for other licensees extend to the
|
||||
entire whole, and thus to each and every part regardless of who wrote it.
|
||||
|
||||
Thus, it is not the intent of this section to claim rights or contest
|
||||
your rights to work written entirely by you; rather, the intent is to
|
||||
exercise the right to control the distribution of derivative or
|
||||
collective works based on the Program.
|
||||
|
||||
In addition, mere aggregation of another work not based on the Program
|
||||
with the Program (or with a work based on the Program) on a volume of
|
||||
a storage or distribution medium does not bring the other work under
|
||||
the scope of this License.
|
||||
|
||||
3. You may copy and distribute the Program (or a work based on it,
|
||||
under Section 2) in object code or executable form under the terms of
|
||||
Sections 1 and 2 above provided that you also do one of the following:
|
||||
|
||||
a) Accompany it with the complete corresponding machine-readable
|
||||
source code, which must be distributed under the terms of Sections
|
||||
1 and 2 above on a medium customarily used for software interchange; or,
|
||||
|
||||
b) Accompany it with a written offer, valid for at least three
|
||||
years, to give any third party, for a charge no more than your
|
||||
cost of physically performing source distribution, a complete
|
||||
machine-readable copy of the corresponding source code, to be
|
||||
distributed under the terms of Sections 1 and 2 above on a medium
|
||||
customarily used for software interchange; or,
|
||||
|
||||
c) Accompany it with the information you received as to the offer
|
||||
to distribute corresponding source code. (This alternative is
|
||||
allowed only for noncommercial distribution and only if you
|
||||
received the program in object code or executable form with such
|
||||
an offer, in accord with Subsection b above.)
|
||||
|
||||
The source code for a work means the preferred form of the work for
|
||||
making modifications to it. For an executable work, complete source
|
||||
code means all the source code for all modules it contains, plus any
|
||||
associated interface definition files, plus the scripts used to
|
||||
control compilation and installation of the executable. However, as a
|
||||
special exception, the source code distributed need not include
|
||||
anything that is normally distributed (in either source or binary
|
||||
form) with the major components (compiler, kernel, and so on) of the
|
||||
operating system on which the executable runs, unless that component
|
||||
itself accompanies the executable.
|
||||
|
||||
If distribution of executable or object code is made by offering
|
||||
access to copy from a designated place, then offering equivalent
|
||||
access to copy the source code from the same place counts as
|
||||
distribution of the source code, even though third parties are not
|
||||
compelled to copy the source along with the object code.
|
||||
|
||||
4. You may not copy, modify, sublicense, or distribute the Program
|
||||
except as expressly provided under this License. Any attempt
|
||||
otherwise to copy, modify, sublicense or distribute the Program is
|
||||
void, and will automatically terminate your rights under this License.
|
||||
However, parties who have received copies, or rights, from you under
|
||||
this License will not have their licenses terminated so long as such
|
||||
parties remain in full compliance.
|
||||
|
||||
5. You are not required to accept this License, since you have not
|
||||
signed it. However, nothing else grants you permission to modify or
|
||||
distribute the Program or its derivative works. These actions are
|
||||
prohibited by law if you do not accept this License. Therefore, by
|
||||
modifying or distributing the Program (or any work based on the
|
||||
Program), you indicate your acceptance of this License to do so, and
|
||||
all its terms and conditions for copying, distributing or modifying
|
||||
the Program or works based on it.
|
||||
|
||||
6. Each time you redistribute the Program (or any work based on the
|
||||
Program), the recipient automatically receives a license from the
|
||||
original licensor to copy, distribute or modify the Program subject to
|
||||
these terms and conditions. You may not impose any further
|
||||
restrictions on the recipients' exercise of the rights granted herein.
|
||||
You are not responsible for enforcing compliance by third parties to
|
||||
this License.
|
||||
|
||||
7. If, as a consequence of a court judgment or allegation of patent
|
||||
infringement or for any other reason (not limited to patent issues),
|
||||
conditions are imposed on you (whether by court order, agreement or
|
||||
otherwise) that contradict the conditions of this License, they do not
|
||||
excuse you from the conditions of this License. If you cannot
|
||||
distribute so as to satisfy simultaneously your obligations under this
|
||||
License and any other pertinent obligations, then as a consequence you
|
||||
may not distribute the Program at all. For example, if a patent
|
||||
license would not permit royalty-free redistribution of the Program by
|
||||
all those who receive copies directly or indirectly through you, then
|
||||
the only way you could satisfy both it and this License would be to
|
||||
refrain entirely from distribution of the Program.
|
||||
|
||||
If any portion of this section is held invalid or unenforceable under
|
||||
any particular circumstance, the balance of the section is intended to
|
||||
apply and the section as a whole is intended to apply in other
|
||||
circumstances.
|
||||
|
||||
It is not the purpose of this section to induce you to infringe any
|
||||
patents or other property right claims or to contest validity of any
|
||||
such claims; this section has the sole purpose of protecting the
|
||||
integrity of the free software distribution system, which is
|
||||
implemented by public license practices. Many people have made
|
||||
generous contributions to the wide range of software distributed
|
||||
through that system in reliance on consistent application of that
|
||||
system; it is up to the author/donor to decide if he or she is willing
|
||||
to distribute software through any other system and a licensee cannot
|
||||
impose that choice.
|
||||
|
||||
This section is intended to make thoroughly clear what is believed to
|
||||
be a consequence of the rest of this License.
|
||||
|
||||
8. If the distribution and/or use of the Program is restricted in
|
||||
certain countries either by patents or by copyrighted interfaces, the
|
||||
original copyright holder who places the Program under this License
|
||||
may add an explicit geographical distribution limitation excluding
|
||||
those countries, so that distribution is permitted only in or among
|
||||
countries not thus excluded. In such case, this License incorporates
|
||||
the limitation as if written in the body of this License.
|
||||
|
||||
9. The Free Software Foundation may publish revised and/or new versions
|
||||
of the General Public License from time to time. Such new versions will
|
||||
be similar in spirit to the present version, but may differ in detail to
|
||||
address new problems or concerns.
|
||||
|
||||
Each version is given a distinguishing version number. If the Program
|
||||
specifies a version number of this License which applies to it and "any
|
||||
later version", you have the option of following the terms and conditions
|
||||
either of that version or of any later version published by the Free
|
||||
Software Foundation. If the Program does not specify a version number of
|
||||
this License, you may choose any version ever published by the Free Software
|
||||
Foundation.
|
||||
|
||||
10. If you wish to incorporate parts of the Program into other free
|
||||
programs whose distribution conditions are different, write to the author
|
||||
to ask for permission. For software which is copyrighted by the Free
|
||||
Software Foundation, write to the Free Software Foundation; we sometimes
|
||||
make exceptions for this. Our decision will be guided by the two goals
|
||||
of preserving the free status of all derivatives of our free software and
|
||||
of promoting the sharing and reuse of software generally.
|
||||
|
||||
NO WARRANTY
|
||||
|
||||
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
|
||||
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
|
||||
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
|
||||
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
|
||||
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
|
||||
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
|
||||
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
|
||||
REPAIR OR CORRECTION.
|
||||
|
||||
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
||||
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
|
||||
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
|
||||
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
|
||||
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
|
||||
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
|
||||
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
|
||||
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
|
||||
POSSIBILITY OF SUCH DAMAGES.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
How to Apply These Terms to Your New Programs
|
||||
|
||||
If you develop a new program, and you want it to be of the greatest
|
||||
possible use to the public, the best way to achieve this is to make it
|
||||
free software which everyone can redistribute and change under these terms.
|
||||
|
||||
To do so, attach the following notices to the program. It is safest
|
||||
to attach them to the start of each source file to most effectively
|
||||
convey the exclusion of warranty; and each file should have at least
|
||||
the "copyright" line and a pointer to where the full notice is found.
|
||||
|
||||
<one line to give the program's name and a brief idea of what it does.>
|
||||
Copyright (C) <year> <name of author>
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along
|
||||
with this program; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
|
||||
Also add information on how to contact you by electronic and paper mail.
|
||||
|
||||
If the program is interactive, make it output a short notice like this
|
||||
when it starts in an interactive mode:
|
||||
|
||||
Gnomovision version 69, Copyright (C) year name of author
|
||||
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
|
||||
This is free software, and you are welcome to redistribute it
|
||||
under certain conditions; type `show c' for details.
|
||||
|
||||
The hypothetical commands `show w' and `show c' should show the appropriate
|
||||
parts of the General Public License. Of course, the commands you use may
|
||||
be called something other than `show w' and `show c'; they could even be
|
||||
mouse-clicks or menu items--whatever suits your program.
|
||||
|
||||
You should also get your employer (if you work as a programmer) or your
|
||||
school, if any, to sign a "copyright disclaimer" for the program, if
|
||||
necessary. Here is a sample; alter the names:
|
||||
|
||||
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
|
||||
`Gnomovision' (which makes passes at compilers) written by James Hacker.
|
||||
|
||||
<signature of Ty Coon>, 1 April 1989
|
||||
Ty Coon, President of Vice
|
||||
|
||||
This General Public License does not permit incorporating your program into
|
||||
proprietary programs. If your program is a subroutine library, you may
|
||||
consider it more useful to permit linking proprietary applications with the
|
||||
library. If this is what you want to do, use the GNU Lesser General
|
||||
Public License instead of this License.
|
|
@ -0,0 +1,549 @@
|
|||
=================================================
|
||||
Minetest World Format used as of 0.4.dev-20120322
|
||||
=================================================
|
||||
|
||||
This applies to a world format carrying the block serialization version 22
|
||||
which is used at least in version 0.4.dev-20120322.
|
||||
|
||||
The block serialization version used is 22. It does not fully specify every
|
||||
aspect of this format; if compliance with this format is to be checked, it
|
||||
needs to be done by detecting if the files and data indeed follows it.
|
||||
|
||||
Legacy stuff
|
||||
=============
|
||||
Data can, in theory, be contained in the flat file directory structure
|
||||
described below in Version 17, but it is not officially supported. Also you
|
||||
may stumble upon all kinds of oddities in not-so-recent formats.
|
||||
|
||||
Files
|
||||
======
|
||||
Everything is contained in a directory, the name of which is freeform, but
|
||||
often serves as the name of the world.
|
||||
|
||||
Currently the authentication and ban data is stored on a per-world basis. It
|
||||
can be copied over from an old world to a newly created world.
|
||||
|
||||
World
|
||||
|-- auth.txt ----- Authentication data
|
||||
|-- env_meta.txt - Environment metadata
|
||||
|-- ipban.txt ---- Banned ips/users
|
||||
|-- map_meta.txt - Map metadata
|
||||
|-- map.sqlite --- Map data
|
||||
|-- players ------ Player directory
|
||||
| |-- player1 -- Player file
|
||||
| '-- Foo ------ Player file
|
||||
`-- world.mt ----- World metadata
|
||||
|
||||
auth.txt
|
||||
---------
|
||||
Contains authentication data, player per line.
|
||||
<name>:<password hash>:<privilege1,...>
|
||||
Format of password hash is <name><password> SHA1'd, in the base64 encoding.
|
||||
|
||||
Example lines:
|
||||
- Player "celeron55", no password, privileges "interact" and "shout":
|
||||
celeron55::interact,shout
|
||||
- Player "Foo", password "bar", privilege "shout":
|
||||
foo:iEPX+SQWIR3p67lj/0zigSWTKHg:shout
|
||||
- Player "bar", no password, no privileges:
|
||||
bar::
|
||||
|
||||
env_meta.txt
|
||||
-------------
|
||||
Simple global environment variables.
|
||||
Example content (added indentation):
|
||||
game_time = 73471
|
||||
time_of_day = 19118
|
||||
EnvArgsEnd
|
||||
|
||||
ipban.txt
|
||||
----------
|
||||
Banned IP addresses and usernames.
|
||||
Example content (added indentation):
|
||||
123.456.78.9|foo
|
||||
123.456.78.10|bar
|
||||
|
||||
map_meta.txt
|
||||
-------------
|
||||
Simple global map variables.
|
||||
Example content (added indentation):
|
||||
seed = 7980462765762429666
|
||||
[end_of_params]
|
||||
|
||||
map.sqlite
|
||||
-----------
|
||||
Map data.
|
||||
See Map File Format below.
|
||||
|
||||
player1, Foo
|
||||
-------------
|
||||
Player data.
|
||||
Filename can be anything.
|
||||
See Player File Format below.
|
||||
|
||||
world.mt
|
||||
---------
|
||||
World metadata.
|
||||
Example content (added indentation):
|
||||
gameid = mesetint
|
||||
|
||||
Player File Format
|
||||
===================
|
||||
|
||||
- Should be pretty self-explanatory.
|
||||
- Note: position is in nodes * 10
|
||||
|
||||
Example content (added indentation):
|
||||
hp = 11
|
||||
name = celeron55
|
||||
pitch = 39.77
|
||||
position = (-5231.97,15,1961.41)
|
||||
version = 1
|
||||
yaw = 101.37
|
||||
PlayerArgsEnd
|
||||
List main 32
|
||||
Item default:torch 13
|
||||
Item default:pick_steel 1 50112
|
||||
Item experimental:tnt
|
||||
Item default:cobble 99
|
||||
Item default:pick_stone 1 13104
|
||||
Item default:shovel_steel 1 51838
|
||||
Item default:dirt 61
|
||||
Item default:rail 78
|
||||
Item default:coal_lump 3
|
||||
Item default:cobble 99
|
||||
Item default:leaves 22
|
||||
Item default:gravel 52
|
||||
Item default:axe_steel 1 2045
|
||||
Item default:cobble 98
|
||||
Item default:sand 61
|
||||
Item default:water_source 94
|
||||
Item default:glass 2
|
||||
Item default:mossycobble
|
||||
Item default:pick_steel 1 64428
|
||||
Item animalmaterials:bone
|
||||
Item default:sword_steel
|
||||
Item default:sapling
|
||||
Item default:sword_stone 1 10647
|
||||
Item default:dirt 99
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
EndInventoryList
|
||||
List craft 9
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
EndInventoryList
|
||||
List craftpreview 1
|
||||
Empty
|
||||
EndInventoryList
|
||||
List craftresult 1
|
||||
Empty
|
||||
EndInventoryList
|
||||
EndInventory
|
||||
|
||||
Map File Format
|
||||
================
|
||||
|
||||
Minetest maps consist of MapBlocks, chunks of 16x16x16 nodes.
|
||||
|
||||
In addition to the bulk node data, MapBlocks stored on disk also contain
|
||||
other things.
|
||||
|
||||
History
|
||||
--------
|
||||
We need a bit of history in here. Initially Minetest stored maps in a
|
||||
format called the "sectors" format. It was a directory/file structure like
|
||||
this:
|
||||
sectors2/XXX/ZZZ/YYYY
|
||||
For example, the MapBlock at (0,1,-2) was this file:
|
||||
sectors2/000/ffd/0001
|
||||
|
||||
Eventually Minetest outgrow this directory structure, as filesystems were
|
||||
struggling under the amount of files and directories.
|
||||
|
||||
Large servers seriously needed a new format, and thus the base of the
|
||||
current format was invented, suggested by celeron55 and implemented by
|
||||
JacobF.
|
||||
|
||||
SQLite3 was slammed in, and blocks files were directly inserted as blobs
|
||||
in a single table, indexed by integer primary keys, oddly mangled from
|
||||
coordinates.
|
||||
|
||||
Today we know that SQLite3 allows multiple primary keys (which would allow
|
||||
storing coordinates separately), but the format has been kept unchanged for
|
||||
that part. So, this is where it has come.
|
||||
</history>
|
||||
|
||||
So here goes
|
||||
-------------
|
||||
map.sqlite is an sqlite3 database, containg a single table, called
|
||||
"blocks". It looks like this:
|
||||
|
||||
CREATE TABLE `blocks` (`pos` INT NOT NULL PRIMARY KEY,`data` BLOB);
|
||||
|
||||
The key
|
||||
--------
|
||||
"pos" is created from the three coordinates of a MapBlock using this
|
||||
algorithm, defined here in Python:
|
||||
|
||||
def getBlockAsInteger(p):
|
||||
return int64(p[2]*16777216 + p[1]*4096 + p[0])
|
||||
|
||||
def int64(u):
|
||||
while u >= 2**63:
|
||||
u -= 2**64
|
||||
while u <= -2**63:
|
||||
u += 2**64
|
||||
return u
|
||||
|
||||
It can be converted the other way by using this code:
|
||||
|
||||
def getIntegerAsBlock(i):
|
||||
x = unsignedToSigned(i % 4096, 2048)
|
||||
i = int((i - x) / 4096)
|
||||
y = unsignedToSigned(i % 4096, 2048)
|
||||
i = int((i - y) / 4096)
|
||||
z = unsignedToSigned(i % 4096, 2048)
|
||||
return x,y,z
|
||||
|
||||
def unsignedToSigned(i, max_positive):
|
||||
if i < max_positive:
|
||||
return i
|
||||
else:
|
||||
return i - 2*max_positive
|
||||
|
||||
The blob
|
||||
---------
|
||||
The blob is the data that would have otherwise gone into the file.
|
||||
|
||||
See below for description.
|
||||
|
||||
MapBlock serialization format
|
||||
==============================
|
||||
NOTE: Byte order is MSB first (big-endian).
|
||||
NOTE: Zlib data is in such a format that Python's zlib at least can
|
||||
directly decompress.
|
||||
|
||||
u8 version
|
||||
- map format version number, this one is version 22
|
||||
|
||||
u8 flags
|
||||
- Flag bitmasks:
|
||||
- 0x01: is_underground: Should be set to 0 if there will be no light
|
||||
obstructions above the block. If/when sunlight of a block is updated
|
||||
and there is no block above it, this value is checked for determining
|
||||
whether sunlight comes from the top.
|
||||
- 0x02: day_night_differs: Whether the lighting of the block is different
|
||||
on day and night. Only blocks that have this bit set are updated when
|
||||
day transforms to night.
|
||||
- 0x04: lighting_expired: If true, lighting is invalid and should be
|
||||
updated. If you can't calculate lighting in your generator properly,
|
||||
you could try setting this 1 to everything and setting the uppermost
|
||||
block in every sector as is_underground=0. I am quite sure it doesn't
|
||||
work properly, though.
|
||||
- 0x08: generated: True if the block has been generated. If false, block
|
||||
is mostly filled with CONTENT_IGNORE and is likely to contain eg. parts
|
||||
of trees of neighboring blocks.
|
||||
|
||||
u8 content_width
|
||||
- Number of bytes in the content (param0) fields of nodes
|
||||
- Always 1
|
||||
|
||||
u8 params_width
|
||||
- Number of bytes used for parameters per node
|
||||
- Always 2
|
||||
|
||||
zlib-compressed node data:
|
||||
- content:
|
||||
u8[4096]: param0 fields
|
||||
u8[4096]: param1 fields
|
||||
u8[4096]: param2 fields
|
||||
- The location of a node in each of those arrays is (z*16*16 + y*16 + x).
|
||||
|
||||
zlib-compressed node metadata list
|
||||
- content:
|
||||
u16 version (=1)
|
||||
u16 count of metadata
|
||||
foreach count:
|
||||
u16 position (p.Z*MAP_BLOCKSIZE*MAP_BLOCKSIZE + p.Y*MAP_BLOCKSIZE + p.X)
|
||||
u16 type_id
|
||||
u16 content_size
|
||||
u8[content_size] (content of metadata)
|
||||
|
||||
u16 mapblockobject_count
|
||||
- Always 0
|
||||
- Should be removed in version 23 (TODO)
|
||||
|
||||
u8 static object version:
|
||||
- Always 0
|
||||
|
||||
u16 static_object_count
|
||||
|
||||
foreach static_object_count:
|
||||
u8 type (object type-id)
|
||||
s32 pos_x_nodes * 10000
|
||||
s32 pos_y_nodes * 10000
|
||||
s32 pos_z_nodes * 10000
|
||||
u16 data_size
|
||||
u8[data_size] data
|
||||
|
||||
u32 timestamp
|
||||
- Timestamp when last saved, as seconds from starting the game.
|
||||
- 0xffffffff = invalid/unknown timestamp, nothing should be done with the time
|
||||
difference when loaded
|
||||
|
||||
u8 name-id-mapping version
|
||||
- Always 0
|
||||
|
||||
u16 num_name_id_mappings
|
||||
|
||||
foreach num_name_id_mappings
|
||||
u16 id
|
||||
u16 name_len
|
||||
u8[name_len] name
|
||||
|
||||
EOF.
|
||||
|
||||
Format of nodes
|
||||
----------------
|
||||
A node is composed of the u8 fields param0, param1 and param2.
|
||||
|
||||
The content id of a node is determined as so:
|
||||
- If param0 < 0x80,
|
||||
content_id = param0
|
||||
- Otherwise
|
||||
content_id = (param0<<4) + (param2>>4)
|
||||
|
||||
The purpose of param1 and param2 depend on the definition of the node.
|
||||
|
||||
The name-id-mapping
|
||||
--------------------
|
||||
The mapping maps node content ids to node names.
|
||||
|
||||
Node metadata format
|
||||
---------------------
|
||||
|
||||
1: Generic metadata
|
||||
serialized inventory
|
||||
u32 len
|
||||
u8[len] text
|
||||
u16 len
|
||||
u8[len] owner
|
||||
u16 len
|
||||
u8[len] infotext
|
||||
u16 len
|
||||
u8[len] inventory drawspec
|
||||
u8 allow_text_input (bool)
|
||||
u8 removal_disabled (bool)
|
||||
u8 enforce_owner (bool)
|
||||
u32 num_vars
|
||||
foreach num_vars
|
||||
u16 len
|
||||
u8[len] name
|
||||
u32 len
|
||||
u8[len] value
|
||||
|
||||
14: Sign metadata
|
||||
u16 text_len
|
||||
u8[text_len] text
|
||||
|
||||
15: Chest metadata
|
||||
serialized inventory
|
||||
|
||||
16: Furnace metadata
|
||||
TBD
|
||||
|
||||
17: Locked Chest metadata
|
||||
u16 len
|
||||
u8[len] owner
|
||||
serialized inventory
|
||||
|
||||
Static objects
|
||||
---------------
|
||||
Static objects are persistent freely moving objects in the world.
|
||||
|
||||
Object types:
|
||||
1: Test object
|
||||
2: Item
|
||||
3: Rat (deprecated)
|
||||
4: Oerkki (deprecated)
|
||||
5: Firefly (deprecated)
|
||||
6: MobV2 (deprecated)
|
||||
7: LuaEntity
|
||||
|
||||
1: Item:
|
||||
u8 version
|
||||
version 0:
|
||||
u16 len
|
||||
u8[len] itemstring
|
||||
|
||||
7: LuaEntity:
|
||||
u8 version
|
||||
version 1:
|
||||
u16 len
|
||||
u8[len] entity name
|
||||
u32 len
|
||||
u8[len] static data
|
||||
s16 hp
|
||||
s32 velocity.x * 10000
|
||||
s32 velocity.y * 10000
|
||||
s32 velocity.z * 10000
|
||||
s32 yaw * 1000
|
||||
|
||||
Itemstring format
|
||||
------------------
|
||||
eg. 'default:dirt 5'
|
||||
eg. 'default:pick_wood 21323'
|
||||
eg. '"default:apple" 2'
|
||||
eg. 'default:apple'
|
||||
- The wear value in tools is 0...65535
|
||||
- There are also a number of older formats that you might stumble upon:
|
||||
eg. 'node "default:dirt" 5'
|
||||
eg. 'NodeItem default:dirt 5'
|
||||
eg. 'ToolItem WPick 21323'
|
||||
|
||||
Inventory serialization format
|
||||
-------------------------------
|
||||
- The inventory serialization format is line-based
|
||||
- The newline character used is "\n"
|
||||
- The end condition of a serialized inventory is always "EndInventory\n"
|
||||
- All the slots in a list must always be serialized.
|
||||
|
||||
Example (format does not include "---"):
|
||||
---
|
||||
List foo 4
|
||||
Item default:sapling
|
||||
Item default:sword_stone 1 10647
|
||||
Item default:dirt 99
|
||||
Empty
|
||||
EndInventoryList
|
||||
List bar 9
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
Empty
|
||||
EndInventoryList
|
||||
EndInventory
|
||||
---
|
||||
|
||||
==============================================
|
||||
Minetest World Format used as of 2011-05 or so
|
||||
==============================================
|
||||
|
||||
Map data serialization format version 17.
|
||||
|
||||
0.3.1 does not use this format, but a more recent one. This exists here for
|
||||
historical reasons.
|
||||
|
||||
Directory structure:
|
||||
sectors/XXXXZZZZ or sectors2/XXX/ZZZ
|
||||
XXXX, ZZZZ, XXX and ZZZ being the hexadecimal X and Z coordinates.
|
||||
Under these, the block files are stored, called YYYY.
|
||||
|
||||
There also exists files map_meta.txt and chunk_meta, that are used by the
|
||||
generator. If they are not found or invalid, the generator will currently
|
||||
behave quite strangely.
|
||||
|
||||
The MapBlock file format (sectors2/XXX/ZZZ/YYYY):
|
||||
-------------------------------------------------
|
||||
|
||||
NOTE: Byte order is MSB first.
|
||||
|
||||
u8 version
|
||||
- map format version number, this one is version 17
|
||||
|
||||
u8 flags
|
||||
- Flag bitmasks:
|
||||
- 0x01: is_underground: Should be set to 0 if there will be no light
|
||||
obstructions above the block. If/when sunlight of a block is updated and
|
||||
there is no block above it, this value is checked for determining whether
|
||||
sunlight comes from the top.
|
||||
- 0x02: day_night_differs: Whether the lighting of the block is different on
|
||||
day and night. Only blocks that have this bit set are updated when day
|
||||
transforms to night.
|
||||
- 0x04: lighting_expired: If true, lighting is invalid and should be updated.
|
||||
If you can't calculate lighting in your generator properly, you could try
|
||||
setting this 1 to everything and setting the uppermost block in every
|
||||
sector as is_underground=0. I am quite sure it doesn't work properly,
|
||||
though.
|
||||
|
||||
zlib-compressed map data:
|
||||
- content:
|
||||
u8[4096]: content types
|
||||
u8[4096]: param1 values
|
||||
u8[4096]: param2 values
|
||||
|
||||
zlib-compressed node metadata
|
||||
- content:
|
||||
u16 version (=1)
|
||||
u16 count of metadata
|
||||
foreach count:
|
||||
u16 position (= p.Z*MAP_BLOCKSIZE*MAP_BLOCKSIZE + p.Y*MAP_BLOCKSIZE + p.X)
|
||||
u16 type_id
|
||||
u16 content_size
|
||||
u8[content_size] misc. stuff contained in the metadata
|
||||
|
||||
u16 mapblockobject_count
|
||||
- always write as 0.
|
||||
- if read != 0, just fail.
|
||||
|
||||
foreach mapblockobject_count:
|
||||
- deprecated, should not be used. Length of this data can only be known by
|
||||
properly parsing it. Just hope not to run into any of this.
|
||||
|
||||
u8 static object version:
|
||||
- currently 0
|
||||
|
||||
u16 static_object_count
|
||||
|
||||
foreach static_object_count:
|
||||
u8 type (object type-id)
|
||||
s32 pos_x * 1000
|
||||
s32 pos_y * 1000
|
||||
s32 pos_z * 1000
|
||||
u16 data_size
|
||||
u8[data_size] data
|
||||
|
||||
u32 timestamp
|
||||
- Timestamp when last saved, as seconds from starting the game.
|
||||
- 0xffffffff = invalid/unknown timestamp, nothing will be done with the time
|
||||
difference when loaded (recommended)
|
||||
|
||||
Node metadata format:
|
||||
---------------------
|
||||
|
||||
Sign metadata:
|
||||
u16 string_len
|
||||
u8[string_len] string
|
||||
|
||||
Furnace metadata:
|
||||
TBD
|
||||
|
||||
Chest metadata:
|
||||
TBD
|
||||
|
||||
Locking Chest metadata:
|
||||
u16 string_len
|
||||
u8[string_len] string
|
||||
TBD
|
||||
|
||||
// END
|
||||
|
|
@ -0,0 +1,91 @@
|
|||
.\" Minetest man page
|
||||
.TH minetest 6 "11 March 2012" "" ""
|
||||
|
||||
.SH NAME
|
||||
minetest \- Multiplayer infinite-world block sandbox
|
||||
|
||||
.SH SYNOPSIS
|
||||
.B minetest
|
||||
[ OPTION ... ]
|
||||
|
||||
.SH DESCRIPTION
|
||||
.B Minetest
|
||||
is one of the first InfiniMiner/Minecraft(/whatever) inspired games (started October 2010), with a goal of taking the survival multiplayer gameplay to a slightly different direction.
|
||||
.PP
|
||||
The main design philosophy is to keep it technically simple, stable and portable. It will be kept lightweight enough to run on fairly old hardware.
|
||||
|
||||
.SH OPTIONS
|
||||
.TP
|
||||
\-\-address <value>
|
||||
Address to connect to
|
||||
.TP
|
||||
\-\-config <value>
|
||||
Load configuration from specified file
|
||||
.TP
|
||||
\-\-disable\-unittests
|
||||
Disable unit tests
|
||||
.TP
|
||||
\-\-enable\-unittests
|
||||
Enable unit tests
|
||||
.TP
|
||||
\-\-gameid <value>
|
||||
Set gameid
|
||||
.TP
|
||||
\-\-go
|
||||
Disable main menu
|
||||
.TP
|
||||
\-\-help
|
||||
Show allowed options
|
||||
.TP
|
||||
\-\-logfile <value>
|
||||
Set logfile path (debug.txt)
|
||||
.TP
|
||||
\-\-map\-dir <value>
|
||||
Same as --world (deprecated)
|
||||
.TP
|
||||
\-\-name <value>
|
||||
Set player name
|
||||
.TP
|
||||
\-\-password <value>
|
||||
Set password
|
||||
.TP
|
||||
\-\-port <value>
|
||||
Set network port (UDP) to use
|
||||
.TP
|
||||
\-\-random\-input
|
||||
Enable random user input, for testing
|
||||
.TP
|
||||
\-\-server
|
||||
Run dedicated server
|
||||
.TP
|
||||
\-\-speedtests
|
||||
Run speed tests
|
||||
.TP
|
||||
\-\-info
|
||||
Print more information to console
|
||||
.TP
|
||||
\-\-verbose
|
||||
Print even more information to console
|
||||
.TP
|
||||
\-\-trace
|
||||
Print enormous amounts of information to console
|
||||
.TP
|
||||
\-\-world <value>
|
||||
Set world path
|
||||
|
||||
.SH BUGS
|
||||
Please report all bugs to Perttu Ahola <celeron55@gmail.com>.
|
||||
|
||||
.SH AUTHOR
|
||||
.PP
|
||||
Perttu Ahola <celeron55@gmail.com>
|
||||
and contributors.
|
||||
.PP
|
||||
This man page was originally written by
|
||||
Juhani Numminen <juhaninumminen0@gmail.com>.
|
||||
|
||||
.SH WWW
|
||||
http://c55.me/minetest/
|
||||
|
||||
.SH "SEE ALSO"
|
||||
.BR minetestserver(6)
|
|
@ -0,0 +1,70 @@
|
|||
.\" Minetestserver man page
|
||||
.TH minetestserver 6 "11 March 2012" "" ""
|
||||
|
||||
.SH NAME
|
||||
minetestserver \- Minetest server
|
||||
|
||||
.SH SYNOPSIS
|
||||
.B minetestserver
|
||||
[ OPTION ... ]
|
||||
|
||||
.SH DESCRIPTION
|
||||
.B Minetest
|
||||
is one of the first InfiniMiner/Minecraft(/whatever) inspired games (started October 2010), with a goal of taking the survival multiplayer gameplay to a slightly different direction.
|
||||
.PP
|
||||
The main design philosophy is to keep it technically simple, stable and portable. It will be kept lightweight enough to run on fairly old hardware.
|
||||
|
||||
.SH OPTIONS
|
||||
.TP
|
||||
\-\-config <value>
|
||||
Load configuration from specified file
|
||||
.TP
|
||||
\-\-disable\-unittests
|
||||
Disable unit tests
|
||||
.TP
|
||||
\-\-enable\-unittests
|
||||
Enable unit tests
|
||||
.TP
|
||||
\-\-gameid <value>
|
||||
Set gameid
|
||||
.TP
|
||||
\-\-help
|
||||
Show allowed options
|
||||
.TP
|
||||
\-\-logfile <value>
|
||||
Set logfile path (debug.txt)
|
||||
.TP
|
||||
\-\-map\-dir <value>
|
||||
Same as --world (deprecated)
|
||||
.TP
|
||||
\-\-port <value>
|
||||
Set network port (UDP) to use
|
||||
.TP
|
||||
\-\-info
|
||||
Print more information to console
|
||||
.TP
|
||||
\-\-verbose
|
||||
Print even more information to console
|
||||
.TP
|
||||
\-\-trace
|
||||
Print enormous amounts of information to console
|
||||
.TP
|
||||
\-\-world <value>
|
||||
Set world path
|
||||
|
||||
.SH BUGS
|
||||
Please report all bugs to Perttu Ahola <celeron55@gmail.com>.
|
||||
|
||||
.SH AUTHOR
|
||||
.PP
|
||||
Perttu Ahola <celeron55@gmail.com>
|
||||
and contributors.
|
||||
.PP
|
||||
This man page was originally written by
|
||||
Juhani Numminen <juhaninumminen0@gmail.com>.
|
||||
|
||||
.SH WWW
|
||||
http://c55.me/minetest/
|
||||
|
||||
.SH "SEE ALSO"
|
||||
.BR minetest(6)
|
|
@ -0,0 +1,72 @@
|
|||
Minetest-c55 protocol (incomplete, early draft):
|
||||
Updated 2011-06-18
|
||||
|
||||
A custom protocol over UDP.
|
||||
Integers are big endian.
|
||||
Refer to connection.{h,cpp} for further reference.
|
||||
|
||||
Initialization:
|
||||
- A dummy reliable packet with peer_id=PEER_ID_INEXISTENT=0 is sent to the server:
|
||||
- Actually this can be sent without the reliable packet header, too, i guess,
|
||||
but the sequence number in the header allows the sender to re-send the
|
||||
packet without accidentally getting a double initialization.
|
||||
- Packet content:
|
||||
# Basic header
|
||||
u32 protocol_id = PROTOCOL_ID = 0x4f457403
|
||||
u16 sender_peer_id = PEER_ID_INEXISTENT = 0
|
||||
u8 channel = 0
|
||||
# Reliable packet header
|
||||
u8 type = TYPE_RELIABLE = 3
|
||||
u16 seqnum = SEQNUM_INITIAL = 65500
|
||||
# Original packet header
|
||||
u8 type = TYPE_ORIGINAL = 1
|
||||
# And no actual payload.
|
||||
- Server responds with something like this:
|
||||
- Packet content:
|
||||
# Basic header
|
||||
u32 protocol_id = PROTOCOL_ID = 0x4f457403
|
||||
u16 sender_peer_id = PEER_ID_INEXISTENT = 0
|
||||
u8 channel = 0
|
||||
# Reliable packet header
|
||||
u8 type = TYPE_RELIABLE = 3
|
||||
u16 seqnum = SEQNUM_INITIAL = 65500
|
||||
# Control packet header
|
||||
u8 type = TYPE_CONTROL = 0
|
||||
u8 controltype = CONTROLTYPE_SET_PEER_ID = 1
|
||||
u16 peer_id_new = assigned peer id to client (other than 0 or 1)
|
||||
- Then the connection can be disconnected by sending:
|
||||
- Packet content:
|
||||
# Basic header
|
||||
u32 protocol_id = PROTOCOL_ID = 0x4f457403
|
||||
u16 sender_peer_id = whatever was gotten in CONTROLTYPE_SET_PEER_ID
|
||||
u8 channel = 0
|
||||
# Control packet header
|
||||
u8 type = TYPE_CONTROL = 0
|
||||
u8 controltype = CONTROLTYPE_DISCO = 3
|
||||
|
||||
- Here's a quick untested connect-disconnect done in PHP:
|
||||
# host: ip of server (use gethostbyname(hostname) to get from a dns name)
|
||||
# port: port of server
|
||||
function check_if_minetestserver_up($host, $port)
|
||||
{
|
||||
$socket = socket_create(AF_INET, SOCK_DGRAM, SOL_UDP);
|
||||
$timeout = array("sec" => 1, "usec" => 0);
|
||||
socket_set_option($socket, SOL_SOCKET, SO_RCVTIMEO, $timeout);
|
||||
$buf = "\x4f\x45\x74\x03\x00\x00\x00\x03\xff\xdc\x01";
|
||||
socket_sendto($socket, $buf, strlen($buf), 0, $host, $port);
|
||||
$buf = socket_read($socket, 1000);
|
||||
if($buf != "")
|
||||
{
|
||||
# We got a reply! read the peer id from it.
|
||||
$peer_id = substr($buf, 9, 2);
|
||||
|
||||
# Disconnect
|
||||
$buf = "\x4f\x45\x74\x03".$peer_id."\x00\x00\x03";
|
||||
socket_sendto($socket, $buf, strlen($buf), 0, $host, $port);
|
||||
socket_close($socket);
|
||||
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
## Generic ignorable patterns and files
|
||||
*~
|
||||
.*.swp
|
||||
*bak*
|
||||
tags
|
||||
*.vim
|
||||
|
|
@ -0,0 +1,50 @@
|
|||
The main game for the Minetest game engine [minetest_game]
|
||||
==========================================================
|
||||
|
||||
To build the wholeness of the Minetest project, insert this repository as
|
||||
/games/minetest_game
|
||||
in the Minetest Engine.
|
||||
|
||||
The Minetest Engine can be found in:
|
||||
https://github.com/celeron55/minetest/
|
||||
|
||||
Compatibility
|
||||
--------------
|
||||
The minetest_game github master HEAD is generally compatible with the github
|
||||
master HEAD of minetest.
|
||||
|
||||
Additionally, when the minetest engine is tagged to be a certain version (eg.
|
||||
0.4.dev-20120326), minetest_game is tagged with the version too.
|
||||
|
||||
When stable releases are made, minetest_game is packaged and made available in
|
||||
https://github.com/celeron55/minetest_game/downloads
|
||||
and in case the repository has grown too much, it may be reset. In that sense,
|
||||
this is not a "real" git repository. (Package maintainers please note!)
|
||||
|
||||
License of source code
|
||||
----------------------
|
||||
Copyright (C) 2010-2012 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
See README.txt in each mod directory for information about other authors.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along
|
||||
with this program; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
|
||||
License of media (textures and sounds)
|
||||
--------------------------------------
|
||||
Copyright (C) 2010-2012 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
See README.txt in each mod directory for information about other authors.
|
||||
|
||||
Attribution-ShareAlike 3.0 Unported (CC BY-SA 3.0)
|
||||
http://creativecommons.org/licenses/by-sa/3.0/
|
||||
|
|
@ -0,0 +1,2 @@
|
|||
name = Minetest
|
||||
|
|
@ -0,0 +1,26 @@
|
|||
Minetest 0.4 mod: bucket
|
||||
=========================
|
||||
|
||||
License of source code:
|
||||
-----------------------
|
||||
Copyright (C) 2011-2012 Kahrl <kahrl@gmx.net>
|
||||
Copyright (C) 2011-2012 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
http://www.gnu.org/licenses/gpl-2.0.html
|
||||
|
||||
License of media (textures and sounds)
|
||||
--------------------------------------
|
||||
Attribution-ShareAlike 3.0 Unported (CC BY-SA 3.0)
|
||||
http://creativecommons.org/licenses/by-sa/3.0/
|
||||
|
||||
Authors of media files
|
||||
-----------------------
|
||||
Everything not listed in here:
|
||||
Copyright (C) 2010-2012 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
|
||||
|
|
@ -0,0 +1,2 @@
|
|||
default
|
||||
|
|
@ -0,0 +1,95 @@
|
|||
-- Minetest 0.4 mod: bucket
|
||||
-- See README.txt for licensing and other information.
|
||||
|
||||
minetest.register_alias("bucket", "bucket:bucket_empty")
|
||||
minetest.register_alias("bucket_water", "bucket:bucket_water")
|
||||
minetest.register_alias("bucket_lava", "bucket:bucket_lava")
|
||||
|
||||
minetest.register_craft({
|
||||
output = 'bucket:bucket_empty 1',
|
||||
recipe = {
|
||||
{'default:steel_ingot', '', 'default:steel_ingot'},
|
||||
{'', 'default:steel_ingot', ''},
|
||||
}
|
||||
})
|
||||
|
||||
bucket = {}
|
||||
bucket.liquids = {}
|
||||
|
||||
-- Register a new liquid
|
||||
-- source = name of the source node
|
||||
-- flowing = name of the flowing node
|
||||
-- itemname = name of the new bucket item (or nil if liquid is not takeable)
|
||||
-- inventory_image = texture of the new bucket item (ignored if itemname == nil)
|
||||
-- This function can be called from any mod (that depends on bucket).
|
||||
function bucket.register_liquid(source, flowing, itemname, inventory_image)
|
||||
bucket.liquids[source] = {
|
||||
source = source,
|
||||
flowing = flowing,
|
||||
itemname = itemname,
|
||||
}
|
||||
bucket.liquids[flowing] = bucket.liquids[source]
|
||||
|
||||
if itemname ~= nil then
|
||||
minetest.register_craftitem(itemname, {
|
||||
inventory_image = inventory_image,
|
||||
stack_max = 1,
|
||||
liquids_pointable = true,
|
||||
on_use = function(itemstack, user, pointed_thing)
|
||||
-- Must be pointing to node
|
||||
if pointed_thing.type ~= "node" then
|
||||
return
|
||||
end
|
||||
-- Check if pointing to a liquid
|
||||
n = minetest.env:get_node(pointed_thing.under)
|
||||
if bucket.liquids[n.name] == nil then
|
||||
-- Not a liquid
|
||||
minetest.env:add_node(pointed_thing.above, {name=source})
|
||||
elseif n.name ~= source then
|
||||
-- It's a liquid
|
||||
minetest.env:add_node(pointed_thing.under, {name=source})
|
||||
end
|
||||
return {name="bucket:bucket_empty"}
|
||||
end
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
minetest.register_craftitem("bucket:bucket_empty", {
|
||||
inventory_image = "bucket.png",
|
||||
stack_max = 1,
|
||||
liquids_pointable = true,
|
||||
on_use = function(itemstack, user, pointed_thing)
|
||||
-- Must be pointing to node
|
||||
if pointed_thing.type ~= "node" then
|
||||
return
|
||||
end
|
||||
-- Check if pointing to a liquid source
|
||||
n = minetest.env:get_node(pointed_thing.under)
|
||||
liquiddef = bucket.liquids[n.name]
|
||||
if liquiddef ~= nil and liquiddef.source == n.name and liquiddef.itemname ~= nil then
|
||||
minetest.env:add_node(pointed_thing.under, {name="air"})
|
||||
return {name=liquiddef.itemname}
|
||||
end
|
||||
end,
|
||||
})
|
||||
|
||||
bucket.register_liquid(
|
||||
"default:water_source",
|
||||
"default:water_flowing",
|
||||
"bucket:bucket_water",
|
||||
"bucket_water.png"
|
||||
)
|
||||
|
||||
bucket.register_liquid(
|
||||
"default:lava_source",
|
||||
"default:lava_flowing",
|
||||
"bucket:bucket_lava",
|
||||
"bucket_lava.png"
|
||||
)
|
||||
|
||||
minetest.register_craft({
|
||||
type = "fuel",
|
||||
recipe = "default:bucket_lava",
|
||||
burntime = 60,
|
||||
})
|
After Width: | Height: | Size: 329 B |
After Width: | Height: | Size: 363 B |
After Width: | Height: | Size: 369 B |
|
@ -0,0 +1,108 @@
|
|||
local function handle_give_command(cmd, giver, receiver, stackstring)
|
||||
if not minetest.get_player_privs(giver)["give"] then
|
||||
minetest.chat_send_player(giver, "error: you don't have permission to give")
|
||||
return
|
||||
end
|
||||
minetest.debug("DEBUG: "..cmd..' invoked, stackstring="'..stackstring..'"')
|
||||
minetest.log(cmd..' invoked, stackstring="'..stackstring..'"')
|
||||
local itemstack = ItemStack(stackstring)
|
||||
if itemstack:is_empty() then
|
||||
minetest.chat_send_player(giver, 'error: cannot give an empty item')
|
||||
return
|
||||
elseif not itemstack:is_known() then
|
||||
minetest.chat_send_player(giver, 'error: cannot give an unknown item')
|
||||
return
|
||||
end
|
||||
local receiverref = minetest.env:get_player_by_name(receiver)
|
||||
if receiverref == nil then
|
||||
minetest.chat_send_player(giver, receiver..' is not a known player')
|
||||
return
|
||||
end
|
||||
local leftover = receiverref:get_inventory():add_item("main", itemstack)
|
||||
if leftover:is_empty() then
|
||||
partiality = ""
|
||||
elseif leftover:get_count() == itemstack:get_count() then
|
||||
partiality = "could not be "
|
||||
else
|
||||
partiality = "partially "
|
||||
end
|
||||
-- The actual item stack string may be different from what the "giver"
|
||||
-- entered (e.g. big numbers are always interpreted as 2^16-1).
|
||||
stackstring = itemstack:to_string()
|
||||
if giver == receiver then
|
||||
minetest.chat_send_player(giver, '"'..stackstring
|
||||
..'" '..partiality..'added to inventory.');
|
||||
else
|
||||
minetest.chat_send_player(giver, '"'..stackstring
|
||||
..'" '..partiality..'added to '..receiver..'\'s inventory.');
|
||||
minetest.chat_send_player(receiver, '"'..stackstring
|
||||
..'" '..partiality..'added to inventory.');
|
||||
end
|
||||
end
|
||||
|
||||
minetest.register_on_chat_message(function(name, message)
|
||||
--print("default on_chat_message: name="..dump(name).." message="..dump(message))
|
||||
local cmd = "/giveme"
|
||||
if message:sub(0, #cmd) == cmd then
|
||||
local stackstring = string.match(message, cmd.." (.*)")
|
||||
if stackstring == nil then
|
||||
minetest.chat_send_player(name, 'usage: '..cmd..' stackstring')
|
||||
return true -- Handled chat message
|
||||
end
|
||||
handle_give_command(cmd, name, name, stackstring)
|
||||
return true
|
||||
end
|
||||
local cmd = "/give"
|
||||
if message:sub(0, #cmd) == cmd then
|
||||
local receiver, stackstring = string.match(message, cmd.." ([%a%d_-]+) (.*)")
|
||||
if receiver == nil or stackstring == nil then
|
||||
minetest.chat_send_player(name, 'usage: '..cmd..' name stackstring')
|
||||
return true -- Handled chat message
|
||||
end
|
||||
handle_give_command(cmd, name, receiver, stackstring)
|
||||
return true
|
||||
end
|
||||
local cmd = "/spawnentity"
|
||||
if message:sub(0, #cmd) == cmd then
|
||||
if not minetest.get_player_privs(name)["give"] then
|
||||
minetest.chat_send_player(name, "you don't have permission to spawn (give)")
|
||||
return true -- Handled chat message
|
||||
end
|
||||
if not minetest.get_player_privs(name)["interact"] then
|
||||
minetest.chat_send_player(name, "you don't have permission to interact")
|
||||
return true -- Handled chat message
|
||||
end
|
||||
local entityname = string.match(message, cmd.." (.*)")
|
||||
if entityname == nil then
|
||||
minetest.chat_send_player(name, 'usage: '..cmd..' entityname')
|
||||
return true -- Handled chat message
|
||||
end
|
||||
print(cmd..' invoked, entityname="'..entityname..'"')
|
||||
local player = minetest.env:get_player_by_name(name)
|
||||
if player == nil then
|
||||
print("Unable to spawn entity, player is nil")
|
||||
return true -- Handled chat message
|
||||
end
|
||||
local p = player:getpos()
|
||||
p.y = p.y + 1
|
||||
minetest.env:add_entity(p, entityname)
|
||||
minetest.chat_send_player(name, '"'..entityname
|
||||
..'" spawned.');
|
||||
return true -- Handled chat message
|
||||
end
|
||||
local cmd = "/pulverize"
|
||||
if message:sub(0, #cmd) == cmd then
|
||||
local player = minetest.env:get_player_by_name(name)
|
||||
if player == nil then
|
||||
print("Unable to pulverize, player is nil")
|
||||
return true -- Handled chat message
|
||||
end
|
||||
if player:get_wielded_item():is_empty() then
|
||||
minetest.chat_send_player(name, 'Unable to pulverize, no item in hand.')
|
||||
else
|
||||
player:set_wielded_item(nil)
|
||||
minetest.chat_send_player(name, 'An item was pulverized.')
|
||||
end
|
||||
return true
|
||||
end
|
||||
end)
|
|
@ -0,0 +1,70 @@
|
|||
Minetest 0.4 mod: default
|
||||
==========================
|
||||
|
||||
License of source code:
|
||||
-----------------------
|
||||
Copyright (C) 2011-2012 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
http://www.gnu.org/licenses/gpl-2.0.html
|
||||
|
||||
License of media (textures and sounds)
|
||||
--------------------------------------
|
||||
Attribution-ShareAlike 3.0 Unported (CC BY-SA 3.0)
|
||||
http://creativecommons.org/licenses/by-sa/3.0/
|
||||
|
||||
Authors of media files
|
||||
-----------------------
|
||||
Everything not listed in here:
|
||||
Copyright (C) 2010-2012 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
|
||||
Originating from work by kddekadenz/Dogers:
|
||||
default_grass_footstep.{1,2,3}.ogg
|
||||
default_dig_crumbly.{1,2}.ogg
|
||||
|
||||
Popping sound:
|
||||
http://www.youtube.com/watch?v=vJ507XRaslc
|
||||
|
||||
Minecraft textures:
|
||||
http://minetest.net/forum/viewtopic.php?id=997
|
||||
|
||||
Cisoun's WTFPL texture pack:
|
||||
default_chest_front.png
|
||||
default_chest_lock.png
|
||||
default_chest_side.png
|
||||
default_chest_top.png
|
||||
default_cobble.png
|
||||
default_dirt.png
|
||||
default_grass.png
|
||||
default_grass_side.png
|
||||
default_jungletree.png
|
||||
default_jungletree_top.png
|
||||
default_lava.png
|
||||
default_leaves.png
|
||||
default_mossycobble.png
|
||||
default_sand.png
|
||||
default_sapling.png
|
||||
default_sign_wall.png
|
||||
default_stone.png
|
||||
default_tool_mesepick.png
|
||||
default_tool_steelpick.png
|
||||
default_tool_steelshovel.png
|
||||
default_tool_steelsword.png
|
||||
default_tool_stonepick.png
|
||||
default_tool_stoneshovel.png
|
||||
default_tool_woodpick.png
|
||||
default_tool_woodshovel.png
|
||||
default_tree.png
|
||||
default_tree_top.png
|
||||
default_water.png
|
||||
|
||||
Originating from G4JC's Almost MC Texture Pack:
|
||||
default_wood.png
|
||||
default_torch.png
|
||||
default_torch_on_ceiling.png
|
||||
default_torch_on_floor.png
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
-- Furnace (lkjoel)
|
||||
-- Ported from minetest's C++ code
|
||||
|
||||
|
|
@ -0,0 +1,92 @@
|
|||
-- minetest/default/leafdecay.lua
|
||||
|
||||
-- To enable leaf decay for a node, add it to the "leafdecay" group.
|
||||
--
|
||||
-- The rating of the group determines how far from a node in the group "tree"
|
||||
-- the node can be without decaying.
|
||||
--
|
||||
-- If param2 of the node is ~= 0, the node will always be preserved. Thus, if
|
||||
-- the player places a node of that kind, you will want to set param2=1 or so.
|
||||
|
||||
default.leafdecay_trunk_cache = {}
|
||||
default.leafdecay_enable_cache = true
|
||||
-- Spread the load of finding trunks
|
||||
default.leafdecay_trunk_find_allow_accumulator = 0
|
||||
|
||||
minetest.register_globalstep(function(dtime)
|
||||
local finds_per_second = 5000
|
||||
default.leafdecay_trunk_find_allow_accumulator =
|
||||
math.floor(dtime * finds_per_second)
|
||||
end)
|
||||
|
||||
minetest.register_abm({
|
||||
nodenames = {"group:leafdecay"},
|
||||
neighbors = {"air", "group:liquid"},
|
||||
-- A low interval and a high inverse chance spreads the load
|
||||
interval = 2,
|
||||
chance = 5,
|
||||
|
||||
action = function(p0, node, _, _)
|
||||
--print("leafdecay ABM at "..p0.x..", "..p0.y..", "..p0.z..")")
|
||||
local do_preserve = false
|
||||
local d = minetest.registered_nodes[node.name].groups.leafdecay
|
||||
if not d or d == 0 then
|
||||
--print("not groups.leafdecay")
|
||||
return
|
||||
end
|
||||
local n0 = minetest.env:get_node(p0)
|
||||
if n0.param2 ~= 0 then
|
||||
--print("param2 ~= 0")
|
||||
return
|
||||
end
|
||||
local p0_hash = nil
|
||||
if default.leafdecay_enable_cache then
|
||||
p0_hash = minetest.hash_node_position(p0)
|
||||
local trunkp = default.leafdecay_trunk_cache[p0_hash]
|
||||
if trunkp then
|
||||
local n = minetest.env:get_node(trunkp)
|
||||
local reg = minetest.registered_nodes[n.name]
|
||||
-- Assume ignore is a trunk, to make the thing work at the border of the active area
|
||||
if n.name == "ignore" or (reg.groups.tree and reg.groups.tree ~= 0) then
|
||||
--print("cached trunk still exists")
|
||||
return
|
||||
end
|
||||
--print("cached trunk is invalid")
|
||||
-- Cache is invalid
|
||||
table.remove(default.leafdecay_trunk_cache, p0_hash)
|
||||
end
|
||||
end
|
||||
if default.leafdecay_trunk_find_allow_accumulator <= 0 then
|
||||
return
|
||||
end
|
||||
default.leafdecay_trunk_find_allow_accumulator =
|
||||
default.leafdecay_trunk_find_allow_accumulator - 1
|
||||
-- Assume ignore is a trunk, to make the thing work at the border of the active area
|
||||
local p1 = minetest.env:find_node_near(p0, d, {"ignore", "group:tree"})
|
||||
if p1 then
|
||||
do_preserve = true
|
||||
if default.leafdecay_enable_cache then
|
||||
--print("caching trunk")
|
||||
-- Cache the trunk
|
||||
default.leafdecay_trunk_cache[p0_hash] = p1
|
||||
end
|
||||
end
|
||||
if not do_preserve then
|
||||
-- Drop stuff other than the node itself
|
||||
itemstacks = minetest.get_node_drops(n0.name)
|
||||
for _, itemname in ipairs(itemstacks) do
|
||||
if itemname ~= n0.name then
|
||||
local p_drop = {
|
||||
x = p0.x - 0.5 + math.random(),
|
||||
y = p0.y - 0.5 + math.random(),
|
||||
z = p0.z - 0.5 + math.random(),
|
||||
}
|
||||
minetest.env:add_item(p_drop, itemname)
|
||||
end
|
||||
end
|
||||
-- Remove node
|
||||
minetest.env:remove_node(p0)
|
||||
end
|
||||
end
|
||||
})
|
||||
|
|
@ -0,0 +1,230 @@
|
|||
-- minetest/default/mapgen.lua
|
||||
|
||||
--
|
||||
-- Aliases for map generator outputs
|
||||
--
|
||||
|
||||
minetest.register_alias("mapgen_air", "air")
|
||||
minetest.register_alias("mapgen_stone", "default:stone")
|
||||
minetest.register_alias("mapgen_tree", "default:tree")
|
||||
minetest.register_alias("mapgen_jungletree", "default:jungletree")
|
||||
minetest.register_alias("mapgen_leaves", "default:leaves")
|
||||
minetest.register_alias("mapgen_apple", "default:apple")
|
||||
minetest.register_alias("mapgen_water_source", "default:water_source")
|
||||
minetest.register_alias("mapgen_dirt", "default:dirt")
|
||||
minetest.register_alias("mapgen_sand", "default:sand")
|
||||
minetest.register_alias("mapgen_gravel", "default:gravel")
|
||||
minetest.register_alias("mapgen_clay", "default:clay")
|
||||
minetest.register_alias("mapgen_lava_source", "default:lava_source")
|
||||
minetest.register_alias("mapgen_cobble", "default:cobble")
|
||||
minetest.register_alias("mapgen_mossycobble", "default:mossycobble")
|
||||
minetest.register_alias("mapgen_dirt_with_grass", "default:dirt_with_grass")
|
||||
minetest.register_alias("mapgen_junglegrass", "default:junglegrass")
|
||||
minetest.register_alias("mapgen_stone_with_coal", "default:stone_with_coal")
|
||||
minetest.register_alias("mapgen_stone_with_iron", "default:stone_with_iron")
|
||||
minetest.register_alias("mapgen_mese", "default:mese")
|
||||
minetest.register_alias("mapgen_desert_sand", "default:desert_sand")
|
||||
minetest.register_alias("mapgen_desert_stone", "default:desert_stone")
|
||||
-- Nether stuff
|
||||
minetest.register_alias("mapgen_netherrack", "nether:netherrack")
|
||||
minetest.register_alias("mapgen_nether_tree", "nether:nether_tree")
|
||||
minetest.register_alias("mapgen_nether_leaves", "nether:nether_leaves")
|
||||
minetest.register_alias("mapgen_nether_apple", "nether:nether_apple")
|
||||
minetest.register_alias("mapgen_nether_torch", "nether:nether_torch")
|
||||
minetest.register_alias("mapgen_nether_glowstone", "nether:nether_glowstone")
|
||||
|
||||
--
|
||||
-- Ore generation
|
||||
--
|
||||
|
||||
local function generate_ore(name, wherein, minp, maxp, seed, chunks_per_volume, ore_per_chunk, height_min, height_max)
|
||||
if maxp.y < height_min or minp.y > height_max then
|
||||
return
|
||||
end
|
||||
local y_min = math.max(minp.y, height_min)
|
||||
local y_max = math.min(maxp.y, height_max)
|
||||
local volume = (maxp.x-minp.x+1)*(y_max-y_min+1)*(maxp.z-minp.z+1)
|
||||
local pr = PseudoRandom(seed)
|
||||
local num_chunks = math.floor(chunks_per_volume * volume)
|
||||
local chunk_size = 3
|
||||
if ore_per_chunk <= 4 then
|
||||
chunk_size = 2
|
||||
end
|
||||
local inverse_chance = math.floor(chunk_size*chunk_size*chunk_size / ore_per_chunk)
|
||||
--print("generate_ore num_chunks: "..dump(num_chunks))
|
||||
for i=1,num_chunks do
|
||||
local y0 = pr:next(y_min, y_max-chunk_size+1)
|
||||
if y0 >= height_min and y0 <= height_max then
|
||||
local x0 = pr:next(minp.x, maxp.x-chunk_size+1)
|
||||
local z0 = pr:next(minp.z, maxp.z-chunk_size+1)
|
||||
local p0 = {x=x0, y=y0, z=z0}
|
||||
for x1=0,chunk_size-1 do
|
||||
for y1=0,chunk_size-1 do
|
||||
for z1=0,chunk_size-1 do
|
||||
if pr:next(1,inverse_chance) == 1 then
|
||||
local x2 = x0+x1
|
||||
local y2 = y0+y1
|
||||
local z2 = z0+z1
|
||||
local p2 = {x=x2, y=y2, z=z2}
|
||||
if minetest.env:get_node(p2).name == wherein then
|
||||
minetest.env:set_node(p2, {name=name})
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
--print("generate_ore done")
|
||||
end
|
||||
|
||||
function default.make_papyrus(pos, size)
|
||||
for y=0,size-1 do
|
||||
local p = {x=pos.x, y=pos.y+y, z=pos.z}
|
||||
minetest.env:set_node(p, {name="default:papyrus"})
|
||||
end
|
||||
end
|
||||
|
||||
function default.make_cactus(pos, size)
|
||||
for y=0,size-1 do
|
||||
local p = {x=pos.x, y=pos.y+y, z=pos.z}
|
||||
minetest.env:set_node(p, {name="default:cactus"})
|
||||
end
|
||||
end
|
||||
|
||||
minetest.register_on_generated(function(minp, maxp, seed)
|
||||
generate_ore("default:stone_with_coal", "default:stone", minp, maxp, seed, 1/8/8/8, 5, -31000, 64)
|
||||
generate_ore("default:stone_with_iron", "default:stone", minp, maxp, seed+1, 1/16/16/16, 5, -5, 7)
|
||||
generate_ore("default:stone_with_iron", "default:stone", minp, maxp, seed+2, 1/12/12/12, 5, -16, -5)
|
||||
generate_ore("default:stone_with_iron", "default:stone", minp, maxp, seed+3, 1/9/9/9, 5, -31000, -17)
|
||||
generate_ore("gun_powder:gun_stone", "default:stone", minp, maxp, seed+4, 1/9/9/9, 5, -31000, 64)
|
||||
if maxp.y >= 2 and minp.y <= 0 then
|
||||
-- Generate clay
|
||||
-- Assume X and Z lengths are equal
|
||||
local divlen = 4
|
||||
local divs = (maxp.x-minp.x)/divlen+1;
|
||||
for divx=0+1,divs-1-1 do
|
||||
for divz=0+1,divs-1-1 do
|
||||
local cx = minp.x + math.floor((divx+0.5)*divlen)
|
||||
local cz = minp.z + math.floor((divz+0.5)*divlen)
|
||||
if minetest.env:get_node({x=cx,y=1,z=cz}).name == "default:water_source" and
|
||||
minetest.env:get_node({x=cx,y=0,z=cz}).name == "default:sand" then
|
||||
local is_shallow = true
|
||||
local num_water_around = 0
|
||||
if minetest.env:get_node({x=cx-divlen*2,y=1,z=cz+0}).name == "default:water_source" then
|
||||
num_water_around = num_water_around + 1 end
|
||||
if minetest.env:get_node({x=cx+divlen*2,y=1,z=cz+0}).name == "default:water_source" then
|
||||
num_water_around = num_water_around + 1 end
|
||||
if minetest.env:get_node({x=cx+0,y=1,z=cz-divlen*2}).name == "default:water_source" then
|
||||
num_water_around = num_water_around + 1 end
|
||||
if minetest.env:get_node({x=cx+0,y=1,z=cz+divlen*2}).name == "default:water_source" then
|
||||
num_water_around = num_water_around + 1 end
|
||||
if num_water_around >= 2 then
|
||||
is_shallow = false
|
||||
end
|
||||
if is_shallow then
|
||||
for x1=-divlen,divlen do
|
||||
for z1=-divlen,divlen do
|
||||
if minetest.env:get_node({x=cx+x1,y=0,z=cz+z1}).name == "default:sand" then
|
||||
minetest.env:set_node({x=cx+x1,y=0,z=cz+z1}, {name="default:clay"})
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
-- Generate papyrus
|
||||
local perlin1 = minetest.env:get_perlin(354, 3, 0.7, 100)
|
||||
-- Assume X and Z lengths are equal
|
||||
local divlen = 8
|
||||
local divs = (maxp.x-minp.x)/divlen+1;
|
||||
for divx=0,divs-1 do
|
||||
for divz=0,divs-1 do
|
||||
local x0 = minp.x + math.floor((divx+0)*divlen)
|
||||
local z0 = minp.z + math.floor((divz+0)*divlen)
|
||||
local x1 = minp.x + math.floor((divx+1)*divlen)
|
||||
local z1 = minp.z + math.floor((divz+1)*divlen)
|
||||
-- Determine papyrus amount from perlin noise
|
||||
local papyrus_amount = math.floor(perlin1:get2d({x=x0, y=z0}) * 45 - 20)
|
||||
-- Find random positions for papyrus based on this random
|
||||
local pr = PseudoRandom(seed+1)
|
||||
for i=0,papyrus_amount do
|
||||
local x = pr:next(x0, x1)
|
||||
local z = pr:next(z0, z1)
|
||||
if minetest.env:get_node({x=x,y=1,z=z}).name == "default:dirt_with_grass" and
|
||||
minetest.env:find_node_near({x=x,y=1,z=z}, 1, "default:water_source") then
|
||||
default.make_papyrus({x=x,y=2,z=z}, pr:next(2, 4))
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
-- Generate cactuses
|
||||
local perlin1 = minetest.env:get_perlin(230, 3, 0.6, 100)
|
||||
-- Assume X and Z lengths are equal
|
||||
local divlen = 16
|
||||
local divs = (maxp.x-minp.x)/divlen+1;
|
||||
for divx=0,divs-1 do
|
||||
for divz=0,divs-1 do
|
||||
local x0 = minp.x + math.floor((divx+0)*divlen)
|
||||
local z0 = minp.z + math.floor((divz+0)*divlen)
|
||||
local x1 = minp.x + math.floor((divx+1)*divlen)
|
||||
local z1 = minp.z + math.floor((divz+1)*divlen)
|
||||
-- Determine cactus amount from perlin noise
|
||||
local cactus_amount = math.floor(perlin1:get2d({x=x0, y=z0}) * 6 - 3)
|
||||
-- Find random positions for cactus based on this random
|
||||
local pr = PseudoRandom(seed+1)
|
||||
for i=0,cactus_amount do
|
||||
local x = pr:next(x0, x1)
|
||||
local z = pr:next(z0, z1)
|
||||
-- Find ground level (0...15)
|
||||
local ground_y = nil
|
||||
for y=30,0,-1 do
|
||||
if minetest.env:get_node({x=x,y=y,z=z}).name ~= "air" then
|
||||
ground_y = y
|
||||
break
|
||||
end
|
||||
end
|
||||
-- If desert sand, make cactus
|
||||
if ground_y and minetest.env:get_node({x=x,y=ground_y,z=z}).name == "default:desert_sand" then
|
||||
default.make_cactus({x=x,y=ground_y+1,z=z}, pr:next(3, 4))
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
-- Generate dry shrubs
|
||||
local perlin1 = minetest.env:get_perlin(329, 3, 0.6, 100)
|
||||
-- Assume X and Z lengths are equal
|
||||
local divlen = 16
|
||||
local divs = (maxp.x-minp.x)/divlen+1;
|
||||
for divx=0,divs-1 do
|
||||
for divz=0,divs-1 do
|
||||
local x0 = minp.x + math.floor((divx+0)*divlen)
|
||||
local z0 = minp.z + math.floor((divz+0)*divlen)
|
||||
local x1 = minp.x + math.floor((divx+1)*divlen)
|
||||
local z1 = minp.z + math.floor((divz+1)*divlen)
|
||||
-- Determine cactus amount from perlin noise
|
||||
local cactus_amount = math.floor(perlin1:get2d({x=x0, y=z0}) * 5 + 0)
|
||||
-- Find random positions for cactus based on this random
|
||||
local pr = PseudoRandom(seed+1)
|
||||
for i=0,cactus_amount do
|
||||
local x = pr:next(x0, x1)
|
||||
local z = pr:next(z0, z1)
|
||||
-- Find ground level (0...15)
|
||||
local ground_y = nil
|
||||
for y=30,0,-1 do
|
||||
if minetest.env:get_node({x=x,y=y,z=z}).name ~= "air" then
|
||||
ground_y = y
|
||||
break
|
||||
end
|
||||
end
|
||||
-- If desert sand, make cactus
|
||||
if ground_y and minetest.env:get_node({x=x,y=ground_y,z=z}).name == "default:desert_sand" then
|
||||
minetest.env:set_node({x=x,y=ground_y+1,z=z}, {name="default:dry_shrub"})
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
[Dolphin]
|
||||
AdditionalInfoV2=Details_Size,Details_Date,CustomizedDetails
|
||||
Timestamp=2012,4,29,3,45,0
|
||||
Version=2
|
||||
ViewMode=1
|
|
@ -0,0 +1,4 @@
|
|||
Wood:
|
||||
http://www.youtube.com/watch?v=u6UNjvQIurQ&feature=related
|
||||
Grass and Dirt:
|
||||
http://www.freesound.org/people/Snoman/
|
|
@ -0,0 +1,4 @@
|
|||
[Dolphin]
|
||||
AdditionalInfoV2=Details_Size,Details_Date,CustomizedDetails
|
||||
Timestamp=2012,4,21,22,22,53
|
||||
Version=2
|
After Width: | Height: | Size: 1.1 KiB |
After Width: | Height: | Size: 241 B |
After Width: | Height: | Size: 292 B |
After Width: | Height: | Size: 457 B |
After Width: | Height: | Size: 449 B |
After Width: | Height: | Size: 319 B |
After Width: | Height: | Size: 296 B |
After Width: | Height: | Size: 646 B |
After Width: | Height: | Size: 626 B |
After Width: | Height: | Size: 650 B |
After Width: | Height: | Size: 584 B |
After Width: | Height: | Size: 613 B |
After Width: | Height: | Size: 258 B |
After Width: | Height: | Size: 210 B |
After Width: | Height: | Size: 118 B |
After Width: | Height: | Size: 240 B |
After Width: | Height: | Size: 589 B |
After Width: | Height: | Size: 627 B |
After Width: | Height: | Size: 517 B |
After Width: | Height: | Size: 498 B |
After Width: | Height: | Size: 450 B |
After Width: | Height: | Size: 300 B |
After Width: | Height: | Size: 246 B |