# Topic Count Down script by Rosc at rosc2112.net - Nov 2006 - rosc2112 at yahoo com
# Latest version is kept at: http://members.dandy.net/~fbn/tcd.tcl.txt
# Based on date.tcl by Rosc - (Loosely) Based on Date.tcl by Evo|ver @ ircnet
set tcdversion "Topic Count Down v0.1d"
####################################################################################################################
## Purpose:
## Stores events and makes countdown announcements/updates channel topics every xx minutes til event happens. 
#  You can save multiple events, but keep in mind that topic length is limited by the irc server! 
#  
# Usage:       
# To show help file: 
#                   .tcd help  - show the full help file.
# To set an event:
#                   .tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <event-description>
#                                          month day   year hour:minute
#                   The date format is like: JAN 01 2007 21:12  (Hour is in 24hr format: 21:12 == 9:12pm)
#
#                   The option for <#chan:announce|topic|both> means: 
#                       #channelname:public announcements OR set topic OR do both
#
#                   If you want to have the same event announced on multiple channels, simply enter
#                   the same event data with a DIFFERENT <eventname> and <#channelname:option>
#
#         Example: .tcd event geddysbday jul 29 2007 21:12 #mychannel:both Geddy Lee's 53rd Birthday Party!
#         Example: .tcd event geddysbday- jul 29 2007 21:12 #channel2:both Geddy Lee's 53rd Birthday Party!
#
# When reporting bugs, PLEASE include the .set errorInfo debug info! 
# Read here: http://forum.egghelp.org/viewtopic.php?t=10215
#
# Changes:
# Nov 21 2006 - Removed the starting timer, as it's not necessary (tcdannounceevent is called at bottom.)
#             - Made a fallback option if an event does not fit in the channel topic, do announcement instead.
# Nov 23 2006 - Fixed misnamed var 'maxyears'
# Aug 07 2007 - Fixed a typo in a varname.
#
#####################################################################################################################

## Configs

# Channels where we allow public use of the commands.
set tcdpubchans "$tgchan"

# Channels that can be specified in the <#chan:option> parameter (other channels won't be accepted.)
set tcdtopchans "$tgchan"

# name of file where the script stores the data
set tcdeventdatafile "$etname"

# max years into the future we want to store events.  Note: tcl cannot handle dates beyond year 2037
set tcdmaxyears 10

# How often do you want to update the channel topic/make announcements (in minutes)
set tcdupdate 1440

# Max length for eventname (This is a shortname used to identify the event, this will be shown in channel topics.)
set tcdelength 10

# Max length for event descriptions (set this to something reasonable, this will show in channel topics.):
set tcddlength 60

# Your ircd's TOPICLEN (multiple events over this length limit will not be shown in topic.)
set tcdtoplength 307

# Delete past events (1) from the data file, or just leave them for reference (0)?
set tcdeventexpire 1

# What permissions flags does a user need to add events (permissions are checked on the channel the user
# is trying to add an event for.)
set tcdaddperms "-|m"

# What permissions flags does a user need to remove ANY events (users can always remove their *own* events)
# This is a global flag, not channel flag.
set tcdremperms "m"

# If an event calls for changing topics, but the bot doesn't have ops and a channel is set mode +t,  
# fall back to making a public announcement instead of trying to change topic? (0 == no, 1 == yes)
# Don't worry, it will not duplicate announcements if you're already using the 'both' option.
set tcdfallback 1

# If an event won't fit in the topic when 'topic' option is selected, fall back to making an announcement instead?
# (0 == no, 1 == yes) Again, it will not duplicate announcements if you're using the 'both' option.
set tcdsizefb 1

################################################################################################################
# code below #
#------------#
bind pub - .tcd tcdpub_date
bind msg - .tcd tcdmsg_date

proc tcdmsg_date {nick host hand text} {
	# If we don't know the user and they are not on any of our channels, just ignore them.
	if {(![onchan $nick]) && (![validuser $nick])} {
		#puthelp "PRIVMSG $nick :You're not on any of my channels!"
		return
	}
	tcdpub_date $nick $host $hand privmsg $text
}

## proc to handle everything
proc tcdpub_date {nick host hand chan arg} {
	global botnick tcdpubchans tcdtopchans tcdelength tcddlength tcdaddperms
	set arg [lrange [split $arg] 0 end]
	set cmd [lindex $arg 0]
	set tcdeventname [lrange $arg 1 1]
	set tcdmonth [lindex $arg 2];set tcdmonth [string toupper $tcdmonth]
	set tcday [lindex $arg 3]
	set tcdyear [lindex $arg 4]
	set tcdtime [lindex $arg 5]
	set tcdhour [lindex [split $tcdtime :] 0]
	set tcdminute [lindex [split $tcdtime :] 1]
	set chanopts [lindex $arg 6]
	set etchan [lindex [split $chanopts :] 0]
	set etopt [lindex [split $chanopts :] 1]
	set etdescr [lrange $arg 7 end]

	if {([lsearch -exact $tcdpubchans $chan] == -1) && ($chan != "privmsg")} {return}

	# If we don't know the user, we don't want them adding/removing events.
	if {(![matchattr $hand $tcdaddperms $etchan]) && (($cmd == "event") || ($cmd == "remove"))} {
		puthelp "PRIVMSG $nick :You do not have permissions to add/remove events for '$etchan' - sorry."
		return
	}
	# Show user all events in the data file
	if {$cmd == "listall"} {
		tcdlistall $hand listalle "" $chan
		return
	}
	# Show user the next upcoming event by date/time
	if {$cmd == "listnext"} {
		tcdlistall $hand listnextevent "" $chan
		return
	}
	# User wants list of their OWN events
	if {$cmd == "listmine"} {
		tcdlistall $hand listmyevents "" $chan
		return
	}
	# Check for a particular event by name
	if {$cmd == "list"} {
		tcdlistall $hand listeventname $tcdeventname $chan
		return
	}
	if {$cmd == "event"} {
		# user is trying to set an event but using the wrong syntax
		if {($tcdeventname == "") || ($tcdmonth == "") || ($tcday == "") || ($tcdyear == "") || ($tcdtime == "") || ($etchan == "") || ($etopt == "") || ($etdescr == "")} {
			puthelp "PRIVMSG $nick :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
			puthelp "PRIVMSG $nick :Type \002.tcd help\002 for more details."
			return
		} else {
			# check the channel given
			if {[lsearch -exact $tcdtopchans $etchan] == -1} {
				puthelp "PRIVMSG $nick :Invalid channelname given, you may only specify one of: \002$tcdtopchans\002"
				puthelp "PRIVMSG $nick :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
				return
			}
			# check channel option given
			if {($etopt != "announce") && ($etopt != "topic") && ($etopt != "both")} {
				puthelp "PRIVMSG $nick :Invalid channel option given, option must be one of: \002announce, topic, or both"
				puthelp "PRIVMSG $nick :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
				return
			}
			# check for eventname length
			set tcdenamelength [string length [join $tcdeventname]]
			if {$tcdenamelength > $tcdelength} {
				puthelp "PRIVMSG $nick :Eventname truncated to $tcdelength chars (max)"
				set tcdeventname [string replace [join $tcdeventname] $tcdelength end]
				set tcdeventname [split $tcdeventname]
			}
			# check the description length
			set tcdesclen [string length [join $etdescr]]
			if {$tcdesclen > $tcddlength} {
				puthelp "PRIVMSG $nick :Description truncated to $tcddlength chars (max)"
				set etdescr [string replace [join $etdescr] $tcddlength end]
				set etdescr [split $etdescr]
			}
			# ready to roll!
			# format: tcdsetdate handle eventname minute hour month day year channelname chanoption desc
			tcdsetdate $hand $tcdeventname $tcdhour $tcdminute $tcdmonth $tcday $tcdyear $etchan $etopt $etdescr
			return
		}
	}
	if {$cmd == "remove"} {
		if {$tcdeventname== ""} {
			puthelp "PRIVMSG $nick :Please supply an eventname. Format: \002.tcd remove eventname\002"
			puthelp "PRIVMSG $nick :You can list your events with: \002.tcd listmine\002"
			return
		} else {
			tcdeldate $hand $tcdeventname
			return
		}
	}
	if {$cmd == "help"} {
		puthelp "PRIVMSG $nick :\002TCD.tcl\002: Show event countdowns in public msgs and/or channel topics until event occurs."
		puthelp "PRIVMSG $nick :To \002create\002 an event:"
		puthelp "PRIVMSG $nick : \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		puthelp "PRIVMSG $nick : The date format is, for example: JAN 01 2007 21:12 (Time is in 24hr format, 21:12 == 9:12pm)"
		puthelp "PRIVMSG $nick : The option for <#chan:announce|topic|both> means:"
		puthelp "PRIVMSG $nick :     #channelname:make public announcements \002OR\002 set topics \002OR\002 do both"
		puthelp "PRIVMSG $nick : If you want to have the same event shown on multiple channels, simply enter the same event data with a DIFFERENT <eventname> and <#channelname:option>"
		puthelp "PRIVMSG $nick : Note: Only these channels may be specified: \002$tcdtopchans\002"
		puthelp "PRIVMSG $nick : \002Ex\002: .tcd event geddysbday jul 29 2007 21:12 #mychannel:both Geddy Lee's 53rd Birthday Party!"
		puthelp "PRIVMSG $nick :To \002view\002 events:"
		puthelp "PRIVMSG $nick :   \002.tcd list <eventname>\002  - show <eventname> in channel."
		puthelp "PRIVMSG $nick :   \002.tcd listnext\002          - show the next upcoming event(s)."
		puthelp "PRIVMSG $nick :   \002.tcd listmine\002          - show all of YOUR own events."
		puthelp "PRIVMSG $nick :   \002.tcd listall\002           - show ALL events in the datafile."
		puthelp "PRIVMSG $nick :To \002remove\002 a event:"
		puthelp "PRIVMSG $nick :        \002.tcd remove eventname\002 - Remove event by name."
		puthelp "PRIVMSG $nick :Commands can be typed in channel or msg to $botnick"
		puthelp "PRIVMSG $nick :\[end Topic Count Down help\]"
		return
	} else {
		puthelp "PRIVMSG $nick :For full help, type \002.tcd help\002 - To create an event:"
 		puthelp "PRIVMSG $nick :\002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
}


proc tcdlistall {hand cmd tcdeventname chan} {
	global tcdeventdatafile
	if {![file exists $tcdeventdatafile]} {
		puthelp "PRIVMSG [hand2nick $hand] :No data file, nothing to show!"
		return
	} 
	set tcdinput [open $tcdeventdatafile r]
	set eventlines "[split [read $tcdinput] \n]"
	catch {close $tcdinput}
	set cnt 0
	# format: handle eventname minute hour month day year channelname chanoption desc
	if {$cmd == "listalle"} {
		foreach line $eventlines {
			if {$line != ""} {
				puthelp "PRIVMSG [hand2nick $hand] :\002Eventname:\002 [join [lrange $line 1 1]] \002Creator:\002 [lindex $line 0] \002Date:\002 [lrange $line 4 6] [lindex $line 2]:[lindex $line 3] \002Desc:\002 [join [lrange $line 9 end]]"
				incr cnt
			}
		}
		if {$cnt == 0} {
			puthelp "PRIVMSG [hand2nick $hand] :There are no saved events."
			return
		} else {
			puthelp "PRIVMSG [hand2nick $hand] :\[end of events list\]"
			return
		}
	}
	if {$cmd == "listeventname"} {
		# list event by name
		if {$chan == "privmsg"} {set chan [hand2nick $hand]}
		foreach line $eventlines {
			if {[lrange $line 1 1] == "$tcdeventname"} {
				puthelp "PRIVMSG $chan :\002Eventname:\002 [join [lrange $line 1 1]] \002Creator:\002 [lindex $line 0] \002Date:\002 [lrange $line 4 6] [lindex $line 2]:[lindex $line 3] \002Desc:\002 [join [lrange $line 9 end]]"
				incr cnt
			}
		}
		if {$cnt == 0} {puthelp "PRIVMSG [hand2nick $hand] :No event named \002[join $tcdeventname]\002 was found."}
		return
	}
	if {$cmd == "listmyevents"} {
		# list users events
		foreach line $eventlines {
			if {[lindex $line 0] == $hand} {
				puthelp "PRIVMSG [hand2nick $hand] :\002Eventname:\002 [join [lrange $line 1 1]] \002Creator:\002 [lindex $line 0] \002Date:\002 [lrange $line 4 6] [lindex $line 2]:[lindex $line 3] \002Desc:\002 [join [lrange $line 9 end]]"
				incr cnt
			}
		}
		if {$cnt == 0} {
			puthelp "PRIVMSG [hand2nick $hand] :You don't have any saved events."
			return
		} else {
			puthelp "PRIVMSG [hand2nick $hand] :\[end of event list\]"
			return
		}
	}
	if {$cmd == "listnextevent"} {
		if {$chan == "privmsg"} {set chan [hand2nick $hand]}
		# calculate the next upcoming event
		set evnow [unixtime]
		set eventlist "";set eventlist2 "";set evcalc "";set evcalc2 "";set searchfor "";set searchfornum "";set matches ""
		foreach line $eventlines {
			if {$line != ""} {
				lappend eventlist $line
			}
		}
		if {$eventlist != ""} {
			foreach line $eventlist {
				set evdate [clock scan "[lindex $line 4] [lindex $line 5], [lindex $line 6] [lindex $line 2]:[lindex $line 3]"]
				lappend eventlist2 "$evdate $line"
			}
			foreach line $eventlist2 {
				set evdate [lindex $line 0]
				set line [lreplace $line 0 0]
				lappend evcalc "[expr $evdate - $evnow] $line"
			}
			set evcalc [lsort -integer -index 0 $evcalc]
			foreach line $evcalc {
				if {[lindex $line 0] >= 1} {
					lappend evcalc2 $line
				}
			}
			if {$evcalc2 != ""} {
				set searchfor [lindex $evcalc2 0]
				set searchfornum [lindex $searchfor 0]
				set matches [lsearch -regexp -all -inline $evcalc2 $searchfornum]
				if {$matches != ""} {
					foreach line $matches {
						puthelp "PRIVMSG $chan :\002Next Event:\002 [lindex $line 2] \002Event Date:\002 [lrange $line 5 7] [lindex $line 3]:[lindex $line 4] \002Desc\002: [lrange $line 11 end]"
					}
					puthelp "PRIVMSG $chan :\[end of next events list\]"
					return
				}
			} else {
				puthelp "PRIVMSG $chan :Didn't find any upcoming events."
				return
			}
		} else {
			puthelp "PRIVMSG $chan :No events in the data file."
			return
		}
	}
}

## proc for setting the date	
proc tcdsetdate {handle eventname hr min mm dd yy channelname chanoption desc} {
	global tcdeventdatafile tcdmaxyears
	if {[file exists $tcdeventdatafile]} {
		set tcddatedata [open $tcdeventdatafile r]
		while {![eof $tcddatedata]} {
			set curline [gets $tcddatedata]
			set checkevent [lindex [split $curline] 1]
			if {[string equal -nocase $checkevent $eventname]} {
				if {[string tolower [lindex $curline 0]] == [string tolower $handle]} {
					catch {close $tcddatedata}
					puthelp "PRIVMSG [hand2nick $handle] :I already have event named '\002[join $eventname]\002' stored. You can use \002.tcd remove [join $eventname]\002 and re-input the event if you want. Otherwise, use a different eventname. :)"
					puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
					return
				} else {
					catch {close $tcddatedata}
					puthelp "PRIVMSG [hand2nick $handle] :An event named '\002[join $eventname]\002' is already stored, belonging to [lindex $curline 0]. Please use a unique eventname."
					puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
					return
				}
			}
		}
		catch {close $tcddatedata}
	}
        regsub -all {[0-9]} $yy {1} myresult
        if {$myresult != 1111} {
        	puthelp "PRIVMSG [hand2nick $handle] :Please use a 4-digit year like 2001, 1984, 1945, etc."
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
	set nmm [lsearch "JAN FEB MAR APR MAY JUN JUL AUG SEP OCT NOV DEC" $mm]
	if {$nmm == "-1"} {
		puthelp "PRIVMSG [hand2nick $handle] :Please use a 3-letter month abbreviation like: Jan, Feb, Mar, etc..."
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
	regsub -all {[0-9]} $dd {1} myresult
	if {($myresult != 11) || ($dd > 31) || ($dd <= 0)} {
		puthelp "PRIVMSG [hand2nick $handle] :Day of month must be 2 digits, between 01 and 31"
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
	regsub -all {[0-9]} $min {1} myresult
	if {($myresult != 11) || ($min >= 60)} {
		puthelp "PRIVMSG [hand2nick $handle] :Minutes must be 2 digits, between 00 and 59"
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
	regsub -all {[0-9]} $hr {1} myresult
	if {($myresult != 11) || ($hr >= 24)} {
		puthelp "PRIVMSG [hand2nick $handle] :Hours must be 2 digit 24-hour format, between 00 and 23"
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
	# check for valid dates, no future bdays, no past events..and check for tcl's stupid 'clock scan' range limits
	set thisyear [lindex [ctime [unixtime]] 4]
	# check for future dates...tcl barfs on years past 2037 :P
	if {[expr $yy - $thisyear] > $tcdmaxyears} {
		puthelp "PRIVMSG [hand2nick $handle] :The earth will explode in $tcdmaxyears yrs, so we're not keeping track that far ahead :P"
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
	# tcl barfs on dates more than 100 yrs old too..Sorry old folks, can't put your bday here!
	if {[expr $thisyear - $yy] > 100} {
		puthelp "PRIVMSG [hand2nick $handle] :That date is already passed.. Try again :P"
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
	# leap year days - found this elegant solution :)
	set days "31 [clock format [clock scan "03/01/$yy yesterday"] -format %e] 31 30 31 30 31 31 30 31 30 31"
        if {[lindex $days $nmm] < $dd} {
        	puthelp "PRIVMSG [hand2nick $handle] :Erm, $mm doesn't have $dd days."
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
        }
	# now that we have the tcl range limit checks done, we can do a clock scan for more precise dates!
	set thisdate [clock scan "$mm $dd, $yy $hr:$min"]
	if {[unixtime] > $thisdate} {
		puthelp "PRIVMSG [hand2nick $handle] :That date is already passed.. Try again :P"
		puthelp "PRIVMSG [hand2nick $handle] :Use: \002.tcd event <eventname> <MON> <DD> <YYYY> <HR:MN> <#chan:announce|topic|both> <description>\002"
		return
	}
	## All cleaned up, writing the data to the file
	set tcddatedata [open $tcdeventdatafile a]
	# format: handle eventname minute hour month day year channelname chanoption desc
	puts $tcddatedata "$handle $eventname $hr $min $mm $dd $yy $channelname $chanoption $desc"
	flush $tcddatedata
	catch {close $tcddatedata}
	puthelp "PRIVMSG [hand2nick $handle] :Eventname \002[join $eventname]\002 is set for $mm $dd $yy at $hr:$min with desc: [join $desc]"
	tcdannounceevent
}


## proc for deleting date
proc tcdeldate {hand target} {
	global tcdeventdatafile tcdremperms
	if {![file exists $tcdeventdatafile]} {
		puthelp "PRIVMSG [hand2nick $hand] :No data file, nothing to delete!"
		return
	}
	set tcddates ""
	set tcddatedata [open $tcdeventdatafile r]
	while {![eof $tcddatedata]} {
		set curline [gets $tcddatedata]
		if {$curline != ""} {
			set tcddates [linsert $tcddates end $curline]
		}
	}
	catch {close $tcddatedata}
	set tcdlinecount "-1"
	set remcheck ""
	foreach date $tcddates {
		incr tcdlinecount
		if {[string equal -nocase [lrange $date 1 1] $target]} {
			set remcheck [string tolower $date]
			break
		}
	}
	if {$remcheck == "" } {
		puthelp "PRIVMSG [hand2nick $hand] :Event named \002[join $target]\002 not found, try \002.tcd listall\002 to find the eventname."
		return
	}
	# if the event is the user's, or if this user has the special magic tcdremperms, delete the event.
	if {([string tolower $hand] == [string tolower [lindex $date 0]]) || ([matchattr $hand $tcdremperms])} {
		set newdata [lreplace $tcddates $tcdlinecount $tcdlinecount]
		set tcddatedata [open $tcdeventdatafile w]
		foreach newdate $newdata {
			if {$newdate != ""} {
				puts $tcddatedata $newdate
			}
		}
		flush $tcddatedata
		catch {close $tcddatedata}
		puthelp "PRIVMSG [hand2nick $hand] :\002$target\002 has been removed."
		tcdannounceevent
		return
	} else {
		puthelp "PRIVMSG [hand2nick $hand] :Sorry, that event is not yours, so you can't remove it.."
		return
	}
}

proc tcdannounceevent {} {
	global tcdeventdatafile tcdtopchans tcdupdate tcdtoplength tcdeventexpire tcdfallback tcdsizefb
	set enow [unixtime]
	if {![file exists $tcdeventdatafile]} {
		return
	}
	foreach channel $tcdtopchans {
		set etopic($channel) ""
	}
	set etimern "";set edates "";set ediftime 0;set newetime 0;set etlength "";set etoplength ""
	set etcddatedata [open $tcdeventdatafile r]
	set edates [split [read $etcddatedata] \n]
	catch {close $etcddatedata}
	# kill old timers
	foreach t [timers] {
		if {[string equal "tcdannounceevent" [lindex $t 1]]} {
			set etimern [lindex $t 2]
			catch {killtimer $etimern}
		}
	}
	set lineno "-1";set updatelist ""
	foreach date $edates {
		if {$date != ""} {
			incr lineno
			set ename [lrange $date 1 1];set min [lindex $date 3];set hr [lindex $date 2]
			set mm [lindex $date 4];set dd [lindex $date 5]
			set yy [lindex $date 6];set emsg [lrange $date 9 end]
			set newetime [clock scan "$mm $dd, $yy $hr:$min"]
			set ediftime [expr $newetime - $enow]
			if {$tcdeventexpire == 1} {
				# expire old events and remove them, if option is enabled.
				if {$ediftime <= -1} {
					putcmdlog "\002Date.tcl:\002 Old event found/removed: line number [expr $lineno + 1] - [join $date]"
					set updatelist [linsert $updatelist 0 $lineno]
				}
			}
			if {$ediftime > 0} {
				set eventnotify [lindex $date 8]
				set echannel [lindex $date 7]
				if {($eventnotify == "announce") || ($eventnotify == "both")} {
					# send to channels
					puthelp "PRIVMSG $echannel :\002\0030,14*** \00315Timp ramas pana la \0030[join $emsg]:\0039 [string map {weeks {saptamani} days {zile} hours {ore} minutess {minute} seconds {secunde} week {saptamana} day {zi} hour {ora} minute {minut} second {secunda}} [duration $ediftime]] \0030***\002"
				} 
				if {($eventnotify == "topic") || ($eventnotify == "both")} {
					# set topic
					if {(![regexp {t} [lindex [getchanmode $echannel] 0]]) || [botisop $echannel]} {
						set etlength [string length "\002[join $ename]\002 \[[duration $ediftime]\: [join $emsg]\]"]
						set etoplength [string length [join $etopic($echannel)]]
						if {[expr $etlength + $etoplength] <= $tcdtoplength} {
							lappend etopic($echannel) "\002\0030,14*** \00315Timp ramas pana la \0030[join $emsg]:\0039 [string map {weeks {saptamani} days {zile} hours {ore} minutes {minute} seconds {secunde} week {saptamana} day {zi} hour {ora} minute {minut} second {secunda}} [duration $ediftime]] \0030***\002"
						} else {
							if {($tcdsizefb) && ($eventnotify != "both")} {
								#putcmdlog "Topic Count Down script: Event [join $ename] does not fit in channel topic, reverting to announcement.."
								puthelp "PRIVMSG $echannel :Timp ramas pana la [join $emsg]: [string map {weeks {saptamani} days {zile} hours {ore} minutes {minute} seconds {secunde} week {saptamana} day {zi} hour {ora} minute {minut} second {secunda}} [duration $ediftime]]"
							} else {
								putcmdlog "Topic Count Down script: topic length exceeded - cannot add event \002[join $ename]\002 to topic!"
							}
						}
					} elseif {($tcdfallback) && ($eventnotify != "both")} {
						puthelp "PRIVMSG $echannel :Timp ramas pana la [join $emsg]: [string map {weeks {saptamani} days {zile} hours {ore} minutes {minute} seconds {secunde} week {saptamana} day {zi} hour {ora} minute {minut} second {secunda}} [duration $ediftime]]"
					}
				}
			}
		}
	}
	foreach channel $tcdtopchans {
		if {$etopic($channel) != ""} {
			putserv "TOPIC $channel :[join $etopic($channel)]"
		}
	}
	if {$updatelist != ""} {
		# need to write out new data file if we removed old events.
		foreach number $updatelist {
			set edates [lreplace $edates $number $number]
		}
		set etcddatedata [open $tcdeventdatafile w]
		foreach line $edates {
			if {$line != ""} {
				puts $etcddatedata $line
			}
		}
		flush $etcddatedata
		catch {close $etcddatedata}
	}
	if {![string match "*tcdannounceevent*" [timers]]} {timer $tcdupdate tcdannounceevent}
}















proc tcdannounceevent2 {} {
	global tcdeventdatafile tcdtopchans tcdupdate tcdtoplength tcdeventexpire tcdfallback tcdsizefb
	set enow [unixtime]
	if {![file exists $tcdeventdatafile]} {
		return
	}
	foreach channel $tcdtopchans {
		set etopic($channel) ""
	}
	set etimern "";set edates "";set ediftime 0;set newetime 0;set etlength "";set etoplength ""
	set etcddatedata [open $tcdeventdatafile r]
	set edates [split [read $etcddatedata] \n]
	catch {close $etcddatedata}
	set lineno "-1";set updatelist ""
	foreach date $edates {
		if {$date != ""} {
			incr lineno
			set ename [lrange $date 1 1];set min [lindex $date 3];set hr [lindex $date 2]
			set mm [lindex $date 4];set dd [lindex $date 5]
			set yy [lindex $date 6];set emsg [lrange $date 9 end]
			set newetime [clock scan "$mm $dd, $yy $hr:$min"]
			set ediftime [expr $newetime - $enow]
			if {$tcdeventexpire == 1} {
				# expire old events and remove them, if option is enabled.
				if {$ediftime <= -1} {
					putcmdlog "\002Date.tcl:\002 Old event found/removed: line number [expr $lineno + 1] - [join $date]"
					set updatelist [linsert $updatelist 0 $lineno]
				}
			}
			if {$ediftime > 0} {
			  if {$ename=="final"} {
				set eventnotify [lindex $date 8]
				set echannel [lindex $date 7]
				
					return "\002\0030,14*** \00315Timp ramas pana la \0030[join $emsg]:\0039 [string map {weeks {saptamani} days {zile} hours {ore} minutess {minute} seconds {secunde} week {saptamana} day {zi} hour {ora} minute {minut} second {secunda}} [duration $ediftime]] \0030***\002"
			   } 
			}
		}
	}
}
proc tcdannounceevent3 {} {
        global tcdeventdatafile tcdtopchans tcdupdate tcdtoplength tcdeventexpire tcdfallback tcdsizefb
        set enow [unixtime]
        if {![file exists $tcdeventdatafile]} {
                return
        }
        foreach channel $tcdtopchans {
                set etopic($channel) ""
        }
        set etimern "";set edates "";set ediftime 0;set newetime 0;set etlength "";set etoplength ""
        set etcddatedata [open $tcdeventdatafile r]
        set edates [split [read $etcddatedata] \n]
        catch {close $etcddatedata}
        set lineno "-1";set updatelist ""
        foreach date $edates {
                if {$date != ""} {
                        incr lineno
                        set ename [lrange $date 1 1];set min [lindex $date 3];set hr [lindex $date 2]
                        set mm [lindex $date 4];set dd [lindex $date 5]
                        set yy [lindex $date 6];set emsg [lrange $date 9 end]
                        set newetime [clock scan "$mm $dd, $yy $hr:$min"]
                        set ediftime [expr $newetime - $enow]
                        if {$tcdeventexpire == 1} {
                                # expire old events and remove them, if option is enabled.
                                if {$ediftime <= -1} {
                                        putcmdlog "\002Date.tcl:\002 Old event found/removed: line number [expr $lineno + 1] - [join $date]"
                                        set updatelist [linsert $updatelist 0 $lineno]
                                }
                        }
                        if {$ediftime > 0} {
                          if {$ename=="final"} {
                                set eventnotify [lindex $date 8]
                                set echannel [lindex $date 7]

                                        return "<b>Timp ramas pana la [join $emsg]:</b> [string map {weeks {saptamani} days {zile} hours {ore} minutess {minute} seconds {secunde} week {saptamana} day {zi} hour {ora} minute {minut} second {secunda}} [duration $ediftime]]"
                           }
                        }
                }
        }
}





















# Run tcdannounceevent on restart/rehash
# tcdannounceevent
# putlog "$tcdversion by \002Rosc\002 loaded"			
