It is currently March 29th, 2024, 4:45 am

Using Regexp to calculate time?

Get help with creating, editing & fixing problems with skins
User avatar
SilverAzide
Rainmeter Sage
Posts: 2588
Joined: March 23rd, 2015, 5:26 pm

Re: Using Regexp to calculate time?

Post by SilverAzide »

jsmorley wrote:Whew... Yeah.
:lol:

If the OP has not staggered away from this thread dazed and in despair, Mordasius' Sunset-Moonrise skin has a Lua script that calculates the times for dawn, sunrise, sunset, and twilight (in addition to moonrise and moonset), All you need is the lat/long and timezone offset from UTC. I've modified this slightly for my own use here and refactored it for inline Lua. In both these scripts, the first 4 elements of array "sunRiseSetTimes" contains the data you need, in fractional hours (i.e., 6.25 = "6:15 AM"). It appears at first glance that buckb's scripts are slightly more accurate if you want things right down to the second.
Gadgets Wiki GitHub More Gadgets...
User avatar
jsmorley
Developer
Posts: 22628
Joined: April 19th, 2009, 11:02 pm
Location: Fort Hunt, Virginia, USA

Re: Using Regexp to calculate time?

Post by jsmorley »

Well, I concede that the "start of sunset" != "nighttime", but rather the "end of sunset" does. However that is a bridge too far for this boy... ;-)
User avatar
jsmorley
Developer
Posts: 22628
Joined: April 19th, 2009, 11:02 pm
Location: Fort Hunt, Virginia, USA

Re: Using Regexp to calculate time?

Post by jsmorley »

I'm willing to consider a metaphorical "dawn hour" and "twilight hour" though... Good enough for romance writers, good enough for me...

Code: Select all

function Initialize()

	measureRise = SKIN:GetMeasure('MeasureRise')
	measureSet = SKIN:GetMeasure('MeasureSet')
	
end

function Update()

	inSunrise = measureRise:GetStringValue()
	inSunset = measureSet:GetStringValue()
	
	NextChange(inSunrise, inSunset)
	
	return formatString
	
end

function NextChange(inSunrise, inSunset)

	currentTime = os.date('*t')
	secondsSinceMidnight = os.time() - os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=0, min=0, sec=0})
	secondsTilMidnight = os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=23, min=59, sec=59}) - os.time()
	
	riseHour = string.match(inSunrise, '(.-):')
	riseMinute = string.match(inSunrise, '.-:(%d%d)')
	setHour = string.match(inSunset, '(.-):') + 12
	setMinute = string.match(inSunset, '.-:(%d%d)')
	
	if currentTime.hour >= 0 and currentTime.hour < 12 then
		dayStateString = 'Morning'
	elseif currentTime.hour >= 12 and currentTime.hour < setHour then
		dayStateString = 'Afternoon'
	else
		dayStateString = 'Evening'
	end
	
	if os.time() >= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=setHour, min=setMinute})  then
		dayState = 'SunRiseTomorrow'
	elseif os.time() <= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=riseHour, min=riseMinute}) then
		dayState = 'SunRiseToday'
	else
		dayState = 'SunSetToday'
	end
	
	if dayState == 'SunRiseTomorrow' then
		secondsTilChange = secondsTilMidnight + (riseHour * 3600) + (riseMinute * 60)
	end
	
	if dayState == 'SunRiseToday' then
		secondsTilChange = ((riseHour * 3600) + (riseMinute * 60)) - secondsSinceMidnight
	end
	
	if dayState == 'SunSetToday' then
		secondsTilChange = os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=setHour, min=setMinute}) - os.time()
	end
	
	formatTable = ConvertSeconds(secondsTilChange)
	formatString = formatTable.hours..' hours '..formatTable.mins..' minutes '..formatTable.secs..' seconds'
	
	if dayState == 'SunSetToday' then
		if os.time() >= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=riseHour, min=riseMinute}) and os.time() <= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=riseHour+1, min=riseMinute}) then
			sunStateString = 'Dawn'
		else
			sunStateString = 'Daytime'
		end
		changeString = 'Sunset is in '
	else 
		if os.time() >= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=setHour, min=setMinute}) and os.time() <= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=setHour+1, min=setMinute}) then
			sunStateString = 'Twilight'
		else
			sunStateString = 'Nighttime'
		end
		changeString = 'Sunrise is in '
	end
	
	return formatString
	
end


function ConvertSeconds(secondsArg)
   
   local daysDiff = math.floor(secondsArg / 86400)
   local remainder = (secondsArg % 86400)
   local hoursDiff = math.floor(remainder / 3600)
   local remainder = (secondsArg % 3600)
   local minsDiff = math.floor(remainder / 60)
   local secsDiff = (remainder % 60)
   
   local elapsedTable = {days=daysDiff, hours=hoursDiff, mins=minsDiff, secs=secsDiff}   
   
   return elapsedTable
   
end
Changed the .rmskin in https://forum.rainmeter.net/viewtopic.php?p=148313#p148313
BunnyHelp
Posts: 3
Joined: May 6th, 2018, 10:50 pm

Re: Using Regexp to calculate time?

Post by BunnyHelp »

SilverAzide wrote: Also when is the moment of "Dawn"? Do you get it through WebParser measure(s), downloading it?
I probably should've clarified that - I am working with a WebParser alike to the one jsmorley just made.


I also thought that setting the Dawn and Dusk wallpapers could be done half an hour before, and changed half an hour after the actual time that was given by wxdata.weather.com, maybe doing some later tweaking if it seemed odd.

I just started looking at that Lua code, and I'll see if i can re-jigger it to work as I need.


Thank you guys very much for your work!
User avatar
jsmorley
Developer
Posts: 22628
Joined: April 19th, 2009, 11:02 pm
Location: Fort Hunt, Virginia, USA

Re: Using Regexp to calculate time?

Post by jsmorley »

BunnyHelp wrote:I probably should've clarified that - I am working with a WebParser alike to the one jsmorley just made.


I also thought that setting the Dawn and Dusk wallpapers could be done half an hour before, and changed half an hour after the actual time that was given by wxdata.weather.com, maybe doing some later tweaking if it seemed odd.

I just started looking at that Lua code, and I'll see if i can re-jigger it to work as I need.


Thank you guys very much for your work!
Here is the Lua adjusted to return "Dawn" for 1/2 hour before and after "sunrise" and "Twilight" for 1/2 hour before and after "sunset". 1800 seconds is 1/2 hour.

Changed the .rmskin in https://forum.rainmeter.net/viewtopic.php?p=148336#p148336.

Code: Select all

function Initialize()

	measureRise = SKIN:GetMeasure('MeasureRise')
	measureSet = SKIN:GetMeasure('MeasureSet')
	
end

function Update()

	inSunrise = measureRise:GetStringValue()
	inSunset = measureSet:GetStringValue()
	
	NextChange(inSunrise, inSunset)
	
	return formatString
	
end

function NextChange(inSunrise, inSunset)

	currentTime = os.date('*t')
	secondsSinceMidnight = os.time() - os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=0, min=0, sec=0})
	secondsTilMidnight = os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=23, min=59, sec=59}) - os.time()
	
	riseHour = string.match(inSunrise, '(.-):')
	riseMinute = string.match(inSunrise, '.-:(%d%d)')
	setHour = string.match(inSunset, '(.-):') + 12
	setMinute = string.match(inSunset, '.-:(%d%d)')
	
	if currentTime.hour >= 0 and currentTime.hour < 12 then
		dayStateString = 'Morning'
	elseif currentTime.hour >= 12 and currentTime.hour < setHour then
		dayStateString = 'Afternoon'
	else
		dayStateString = 'Evening'
	end
	
	if os.time() >= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=setHour, min=setMinute})  then
		dayState = 'SunRiseTomorrow'
	elseif os.time() <= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=riseHour, min=riseMinute}) then
		dayState = 'SunRiseToday'
	else
		dayState = 'SunSetToday'
	end
	
	if dayState == 'SunRiseTomorrow' then
		secondsTilChange = secondsTilMidnight + (riseHour * 3600) + (riseMinute * 60)
	end
	
	if dayState == 'SunRiseToday' then
		secondsTilChange = ((riseHour * 3600) + (riseMinute * 60)) - secondsSinceMidnight
	end
	
	if dayState == 'SunSetToday' then
		secondsTilChange = os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=setHour, min=setMinute}) - os.time()
	end
	
	formatTable = ConvertSeconds(secondsTilChange)
	formatString = formatTable.hours..' hours '..formatTable.mins..' minutes '..formatTable.secs..' seconds'
	
	if dayState == 'SunSetToday' then
		sunStateString = 'Daytime'
		changeString = 'Sunset is in '
	else 
		sunStateString = 'Nighttime'
		changeString = 'Sunrise is in '
	end

	if os.time() >= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=setHour, min=setMinute}) - 1800 and os.time() <= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=setHour, min=setMinute}) + 1800 then
		sunStateString = 'Twilight'
	end

	if os.time() >= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=riseHour, min=riseMinute}) - 1800 and os.time() <= os.time({year=currentTime.year, month=currentTime.month, day=currentTime.day, hour=riseHour, min=riseMinute}) + 1800 then
		sunStateString = 'Dawn'
	end
	
	return formatString
	
end


function ConvertSeconds(secondsArg)
   
   local daysDiff = math.floor(secondsArg / 86400)
   local remainder = (secondsArg % 86400)
   local hoursDiff = math.floor(remainder / 3600)
   local remainder = (secondsArg % 3600)
   local minsDiff = math.floor(remainder / 60)
   local secsDiff = (remainder % 60)
   
   local elapsedTable = {days=daysDiff, hours=hoursDiff, mins=minsDiff, secs=secsDiff}   
   
   return elapsedTable
   
end
1.jpg
If all you are doing is setting a wallpaper based on Dawn/Daytime/Twilight/Nighttime, you can just use Inline Lua to get the current state of the variable sunStateString, and use an IfMatch to set the wallpaper appropriately. Guess all the rest of the "time until" and such is not needed for that, although you did allude to that in your first post, and so you are dead to me now... However, it doesn't hurt, and you never know when you might want it.

BTW, since it is happening right now here, and just looking out the window, I'd say that 1/2 hour is pretty reasonable for the Mid-Atlantic of the East Coast of the US. Your mileage may vary in Finland or Brazil, but you can play with the "1800" as needed.
You do not have the required permissions to view the files attached to this post.