I'm trying to make a simple script for a game, by changing the time of day, but I want to do it in a fast motion. So this is what I'm talking about:
function disco ( hour, minute)
setTime ( 1, 0 )
SLEEP
setTime ( 2, 0 )
SLEEP
setTime ( 3, 0 )
end
and so on. How would I go about doing this?
12 Answers
Lua doesn't provide a standard sleep function, but there are several ways to implement one, see Sleep Function for detail.
For Linux, this may be the easiest one:
function sleep(n)
os.execute("sleep " .. tonumber(n))
end
In Windows, you can use ping:
function sleep(n)
if n > 0 then os.execute("ping -n " .. tonumber(n+1) .. " localhost > NUL") end
end
The one using select deserves some attention because it is the only portable way to get sub-second resolution:
require "socket"
function sleep(sec)
socket.select(nil, nil, sec)
end
sleep(0.2)
If you have luasocket installed:
local socket = require 'socket'
socket.sleep(0.2)
wxLua has three sleep functions:
local wx = require 'wx'
wx.wxSleep(12) -- sleeps for 12 seconds
wx.wxMilliSleep(1200) -- sleeps for 1200 milliseconds
wx.wxMicroSleep(1200) -- sleeps for 1200 microseconds (if the system supports such resolution)
This homebrew function have precision down to a 10th of a second or less.
function sleep (a)
local sec = tonumber(os.clock() + a);
while (os.clock() < sec) do
end
end
I know this is a super old question, but I stumbled upon it while I was working on something. Here's some code that's working for me...
time=os.time()
wait=5
newtime=time+wait
while (time<newtime)
do
time=os.time()
end
And I needed randomization so I added
math.randomseed(os.time())
math.random(); math.random(); math.random()
randwait = math.random(1,30)
time=os.time()
newtime=time+randwait
while (time<newtime)
do
time=os.time()
end
I needed something simple for a polling script, so I tried the os.execute option from Yu Hao's answer. But at least on my machine, I could no longer terminate the script with Ctrl+C. So I tried a very similar function using io.popen instead, and this one does allow early termination.
function wait (s)
local timer = io.popen("sleep " .. s)
timer:close()
end
You should read this:
There are several solutions and each one has a description, which is important to know.
This is, what I used:
function util.Sleep(s)
if type(s) ~= "number" then
error("Unable to wait if parameter 'seconds' isn't a number: " .. type(s))
end
--
local ntime = os.clock() + s/10
repeat until os.clock() > ntime
end
if you're using a MacBook or UNIX based system, use this:
function wait(time)
if tonumber(time) ~= nil then
os.execute("Sleep "..tonumber(time))
else
os.execute("Sleep "..tonumber("0.1"))
end
wait()
You can use "os.time" or "os.clock" with "while" loop, i prefer "repeat until" loop because its shorter, but they are expensive because they cost full usage of a single core.
If you need something less demanding, you can use various wrappers like wxLua that i use, but sometimes, some of them also got usage penalty, specially annoying in games, so its best to test them and get what is best for your project.
Or you can relay on OS like Windows to do sleep function, using applications that exist in system32, via Batch or PowerShell, using ">nul" to hide it with "os.execute" or "io.popen", like "ping" (localhost/127.0.0.1) with timeout, "choice" (works with XP, newer versions may be different, i prefer it), "timeout" (/nobreak may be useless because all Windows commands can be canceled with CTRL+C). Downside are limited to given OS and number limitation as well as seconds or miliseconds, running it on eg. Linux may need Wine emulation for Windows (if application are written for it). You can also use "sleep" or "start-sleep" (from PowerShell), but since Lua are standalone, most people prefer pure Lua or wrappers, and you can use what suits your project.
The safe function sleep (n) for Lua:
function sleep (n)
while n > 0 do
print("Sleeping for ".. tonumber(n) .." seconds...")
os.execute("ping -n 2 localhost > nul")
n = n-1
end
end
Luaposix' unixstd module provides direct access to the sleep function on POSIX systems, i.e. Linux, MacOS and such.
local unistd = require('posix.unistd')
unistd.sleep(5)
sleep only has a second resolution, but posix.time.nanosleep apparently has nanosecond precision:
local time = require('posix.time')
time.nanosleep({tv_sec=5, tv_nsec=500})
function wait(time)
local duration = os.time() + time
while os.time() < duration do end
end
This is probably one of the easiest ways to add a wait/sleep function to your script