Rob van der Woude's Scripting Pages
Powered by GeSHi

Source code for countdown.cs

(view source code of countdown.cs as plain text)

  1. using System;
  2. using System.Collections.Generic;
  3. using System.Threading;
  4. using System.Text.RegularExpressions;
  5.  
  6.  
  7. namespace RobvanderWoude
  8. {
  9. 	class CountDown
  10. 	{
  11. 		static readonly string progver = "2.01";
  12.  
  13.  
  14. 		static int Main( string[] args )
  15. 		{
  16. 			string prefix = string.Empty;
  17. 			string suffix = string.Empty;
  18. 			bool returnremaining = false;
  19. 			int seconds = 0;
  20.  
  21.  
  22. 			#region Parse Command Line
  23.  
  24. 			if ( args.Length == 0 )
  25. 			{
  26. 				return ShowHelp( );
  27. 			}
  28.  
  29. 			foreach ( string arg in args )
  30. 			{
  31. 				if ( arg == "/?" )
  32. 				{
  33. 					return ShowHelp( );
  34. 				}
  35. 				else if ( arg.ToUpper( ) == "/R" )
  36. 				{
  37. 					if ( returnremaining )
  38. 					{
  39. 						return ShowHelp( "Duplicate command line switch /R" );
  40. 					}
  41. 					returnremaining = true;
  42. 				}
  43. 				else if ( int.TryParse( arg, out int test ) )
  44. 				{
  45. 					if ( seconds == 0 )
  46. 					{
  47. 						seconds = test;
  48. 					}
  49. 					else
  50. 					{
  51. 						return ShowHelp( "Duplicate timeout argument" );
  52. 					}
  53. 				}
  54. 				else if ( string.IsNullOrWhiteSpace( prefix ) )
  55. 				{
  56. 					prefix = arg;
  57. 				}
  58. 				else if ( string.IsNullOrWhiteSpace( suffix ) )
  59. 				{
  60. 					suffix = arg;
  61. 				}
  62. 				else
  63. 				{
  64. 					return ShowHelp( "Invalid or too many command line arguments", arg );
  65. 				}
  66. 			}
  67.  
  68. 			// Enable single command line argument for prefix seconds suffix
  69. 			if ( seconds == 0 && !string.IsNullOrWhiteSpace( prefix ) && string.IsNullOrWhiteSpace( suffix ) )
  70. 			{
  71. 				string pattern = @"^([^\d]*)(\d+)(.*)$";
  72. 				Regex regex = new Regex( pattern );
  73. 				if ( regex.IsMatch( prefix ) )
  74. 				{
  75. 					MatchCollection matches = regex.Matches( prefix );
  76. 					if ( matches.Count == 1 )
  77. 					{
  78. 						if ( matches[0].Groups.Count == 4 )
  79. 						{
  80. 							if ( int.TryParse( matches[0].Groups[2].ToString( ), out seconds ) )
  81. 							{
  82. 								prefix = matches[0].Groups[1].ToString( );
  83. 								suffix = matches[0].Groups[3].ToString( );
  84. 							}
  85. 						}
  86. 					}
  87. 				}
  88. 			}
  89.  
  90. 			if ( seconds < 1 || seconds > 86400 )
  91. 			{
  92. 				return ShowHelp( "Specified timeout ({0}) outside allowed range", seconds.ToString( ) );
  93. 			}
  94.  
  95. 			#endregion Parse Command Line
  96.  
  97.  
  98. 			// Temporarily change console properties
  99. 			Console.CursorVisible = false;
  100. 			Console.TreatControlCAsInput = true;
  101.  
  102. 			// Determine the string length for number of digits
  103. 			int counterlength = seconds.ToString( ).Length;
  104.  
  105. 			// Determine the prefix string length
  106. 			int prefixlength = prefix.Length;
  107.  
  108. 			// Determine the suffix string length
  109. 			int suffixlength = suffix.Length;
  110.  
  111. 			// Display optional message
  112. 			Console.Write( prefix );
  113.  
  114. 			// Clear space on screen for countdown counter value
  115. 			Console.Write( new String( ' ', counterlength + suffixlength ) );
  116.  
  117. 			// Start countdown
  118. 			int countdown = seconds;
  119. 			while ( !Console.KeyAvailable && countdown > 0 )
  120. 			{
  121. 				// Wipe previous countdown counter value from screen
  122. 				Console.Write( new String( '\b', counterlength + suffixlength ) );
  123. 				Console.Write( new String( ' ', counterlength + suffixlength ) );
  124. 				Console.Write( new String( '\b', counterlength + suffixlength ) );
  125. 				Console.Write( "{0," + counterlength + "}", countdown );
  126. 				Console.Write( suffix );
  127. 				countdown -= 1; // decrement countdown counter
  128. 				Thread.Sleep( 1000 ); // wait 1 second
  129. 			}
  130.  
  131. 			// Wipe entire countdown counter line from screen
  132. 			Console.Write( new String( '\b', counterlength + suffixlength + prefixlength ) );
  133. 			Console.Write( new String( ' ', counterlength + suffixlength + prefixlength ) );
  134. 			Console.Write( new String( '\b', counterlength + suffixlength + prefixlength ) );
  135.  
  136. 			// Restore console properties
  137. 			Console.CursorVisible = true;
  138. 			Console.TreatControlCAsInput = false;
  139.  
  140. 			// If a key is pressed to interrupt countdown, remove it from keyboard buffer
  141. 			if ( countdown > 0 && Console.KeyAvailable )
  142. 			{
  143. 				Console.ReadKey( true );
  144. 			}
  145.  
  146. 			// Return code depends on command line switch and on countdown completion
  147. 			if ( returnremaining )
  148. 			{
  149. 				return countdown; // remaining number of seconds (requires /R)
  150. 			}
  151. 			else if ( countdown == 0 )
  152. 			{
  153. 				return 0; // countdown completed
  154. 			}
  155. 			else
  156. 			{
  157. 				return 2; // countdown interrupted (not with /R)
  158. 			}
  159. 		}
  160.  
  161.  
  162. 		static int ShowHelp( params string[] errmsg )
  163. 		{
  164. 			#region Help Text
  165.  
  166. 			/*
  167. 			CountDown,  Version 2.01
  168. 			Count down for the specified number of seconds or until a key is pressed
  169.  
  170. 			Usage:  COUNTDOWN  [ prefix ]  seconds  [ suffix ]  [ /R ]
  171.  
  172. 			   or:  COUNTDOWN  "prefix seconds suffix"  [ /R ]
  173.  
  174. 			Where:  prefix     optional prefix message for the counter, e.g. "Waiting "
  175. 			        seconds    delay in seconds (1 .. 86400 = 1 second .. 24 hours)
  176. 			        suffix     optional suffix message for the counter, e.g. " seconds"
  177. 			        /R         return code equals the number of Remaining seconds
  178. 			                   (default: return code 0 = OK, 1 = errors, 2 = key pressed)
  179.  
  180. 			Note:   COUNTDOWN "Wait " 20 " seconds" is equal to COUNTDOWN "Wait 20 seconds"
  181. 			        In the latter notation the first number on the command line will be
  182. 			        used for seconds, any following number will be included in suffix.
  183.  
  184. 			Written by Rob van der Woude
  185. 			https://www.robvanderwoude.com
  186. 			*/
  187.  
  188. 			#endregion Help Text
  189.  
  190.  
  191. 			#region Error Message
  192.  
  193. 			if ( errmsg.Length > 0 )
  194. 			{
  195. 				List<string> errargs = new List<string>( errmsg );
  196. 				errargs.RemoveAt( 0 );
  197. 				Console.Error.WriteLine( );
  198. 				Console.ForegroundColor = ConsoleColor.Red;
  199. 				Console.Error.Write( "ERROR:\t" );
  200. 				Console.ForegroundColor = ConsoleColor.White;
  201. 				Console.Error.WriteLine( errmsg[0], errargs.ToArray( ) );
  202. 				Console.ResetColor( );
  203. 			}
  204.  
  205. 			#endregion Error Message
  206.  
  207.  
  208. 			#region Display Help Text
  209.  
  210. 			Console.Error.WriteLine( );
  211.  
  212. 			Console.Error.WriteLine( "CountDown,  Version {0}", progver );
  213.  
  214. 			Console.Error.WriteLine( "Count down for the specified number of seconds or until a key is pressed" );
  215.  
  216. 			Console.Error.WriteLine( );
  217.  
  218. 			Console.Error.Write( "Usage:  " );
  219. 			Console.ForegroundColor = ConsoleColor.White;
  220. 			Console.Error.WriteLine( "COUNTDOWN  [ prefix ]  seconds  [ suffix ]  [ /R ]" );
  221. 			Console.ResetColor( );
  222.  
  223. 			Console.Error.WriteLine( );
  224.  
  225. 			Console.Error.Write( "   or:  " );
  226. 			Console.ForegroundColor = ConsoleColor.White;
  227. 			Console.Error.WriteLine( "COUNTDOWN  \"prefix seconds suffix\"  [ /R ]" );
  228. 			Console.ResetColor( );
  229.  
  230. 			Console.Error.WriteLine( );
  231.  
  232. 			Console.Error.Write( "Where:  " );
  233. 			Console.ForegroundColor = ConsoleColor.White;
  234. 			Console.Error.Write( "prefix     " );
  235. 			Console.ResetColor( );
  236. 			Console.Error.WriteLine( "optional prefix message for the counter, e.g. \"Waiting \"" );
  237.  
  238.  
  239. 			Console.ForegroundColor = ConsoleColor.White;
  240. 			Console.Error.Write( "        seconds    " );
  241. 			Console.ResetColor( );
  242. 			Console.Error.WriteLine( "delay in seconds (1 .. 86400 = 1 second .. 24 hours)" );
  243.  
  244. 			Console.ForegroundColor = ConsoleColor.White;
  245. 			Console.Error.Write( "        suffix     " );
  246. 			Console.ResetColor( );
  247. 			Console.Error.WriteLine( "optional suffix message for the counter, e.g. \" seconds\"" );
  248.  
  249. 			Console.ForegroundColor = ConsoleColor.White;
  250. 			Console.Error.Write( "        /R" );
  251. 			Console.ResetColor( );
  252. 			Console.Error.Write( "         return code equals the number of " );
  253. 			Console.ForegroundColor = ConsoleColor.White;
  254. 			Console.Error.Write( "R" );
  255. 			Console.ResetColor( );
  256. 			Console.Error.WriteLine( "emaining seconds" );
  257.  
  258. 			Console.Error.WriteLine( "                   (default: return code 0 = OK, 1 = errors, 2 = key pressed)" );
  259.  
  260. 			Console.Error.WriteLine( );
  261.  
  262. 			Console.Error.Write( "Note:   " );
  263. 			Console.ForegroundColor = ConsoleColor.White;
  264. 			Console.Error.Write( "COUNTDOWN \"Wait \" 20 \" seconds\" " );
  265. 			Console.ResetColor( );
  266. 			Console.Error.Write( "is equal to " );
  267. 			Console.ForegroundColor = ConsoleColor.White;
  268. 			Console.Error.WriteLine( "COUNTDOWN \"Wait 20 seconds\"" );
  269. 			Console.ResetColor( );
  270.  
  271. 			Console.Error.WriteLine( "        In the latter notation the first number on the command line will be" );
  272.  
  273. 			Console.Error.Write( "        used for " );
  274. 			Console.ForegroundColor = ConsoleColor.White;
  275. 			Console.Error.Write( "seconds" );
  276. 			Console.ResetColor( );
  277. 			Console.Error.Write( ", any following number will be included in " );
  278. 			Console.ForegroundColor = ConsoleColor.White;
  279. 			Console.Error.Write( "suffix" );
  280. 			Console.ResetColor( );
  281. 			Console.Error.WriteLine( "." );
  282.  
  283. 			Console.Error.WriteLine( );
  284.  
  285. 			Console.Error.WriteLine( "Written by Rob van der Woude" );
  286.  
  287. 			Console.Error.WriteLine( "https://www.robvanderwoude.com" );
  288.  
  289. 			#endregion Display Help Text
  290.  
  291. 			return 1;
  292. 		}
  293. 	}
  294. }
  295.  

page last uploaded: 2021-01-27, 16:12