anchor.diff:  	{
   		input.onKeyDown.listen((KeyboardEvent key) //onKeyUp seems to be too late to prevent TAB's default behavior
   		{
  +			if(key.keyCode == 38 && inputHistoryPointer < inputHistory.length) //pressed up arrow
  +			{
  +				input.value = inputHistory.elementAt(inputHistoryPointer);
  +				if(inputHistoryPointer < inputHistory.length-1)
  +					inputHistoryPointer++;
  +			}
  +			if(key.keyCode == 40) //pressed down arrow
  +			{
  +				if(inputHistoryPointer > 0)
  +				{
  +					inputHistoryPointer--;
  +					input.value = inputHistory.elementAt(inputHistoryPointer);
  +				}
  +				else
  +					input.value = "";
  +			}
   			if(key.keyCode == 9) //tab key, try to complete a user's name
   			{
   				key.preventDefault();
  
positive.code: 				return;
  			
  			parseInput(input.value);
  			input.value = '';
  		});
  	}
  
negative.code: {
  	static List<String> _COLORS = ["aqua", "blue", "fuchsia", "gray", "green", "lime", "maroon", "navy", "olive", "orange", "purple", "red", "teal"];
  	List<String> connectedUsers = new List();
  	List<String> inputHistory = new List();
  	String channelName, lastWord = "";
  	bool useSpanForTitle, tabInserted = false;
  	WebSocket webSocket;
  	DivElement chatDiv, chatHistory;
  	int unreadMessages = 0, tabSearchIndex = 0, numMessages = 0, inputHistoryPointer = 0;
  	final _chatServerUrl = "ws://couserver.herokuapp.com";
  	
  	TabContent(this.channelName, this.useSpanForTitle)
  