The related source file for 
              this article is found in the "Examples/advancedChat" folder 
              under the name of "advancedChat.fla".  
               
              In this tutorial we will expand the concepts learned so far and 
              we will enhance the "SimpleChat" demo to make it a more 
              advanced chatting application. 
            The picture below shows the main GUI (graphical user interaface) 
              of the "AdvancedChat" 
              
            Here's a list of the features that we're going to add to our previous
            example: 
            - A roomlist: 
              it will show every room available with realtime user count 
              you will be able join any room by clicking on it 
              you will be able to join password protected rooms 
              you will be able to create new rooms (with password also) 
               
              - A better UserList: 
              by clicking on one user you will be able to send a private message 
               
              - An exit button: 
              by clicking it you will log out of the chat. 
             
             
              [ THE ROOMLIST ] 
              By opening the source .FLA file you will notice that the code in 
              the first two labels is almost identical to the previous sample, 
              so you can safely position the playhead on the "chat" 
              label. 
            The first thing you should notice in the GUI is the presence of
              a new listbox called roomList_lb. 
            Now open the Actionscript panel (F9) and inspect the code for
              the onRoomListUpdate() event: 
            - smartfox.onRoomListUpdate = function(roomList)
 
- {
 
	- roomList_lb.removeAll()
 
- for (var i in roomList)
 
	- {
 
		- var room = roomList[i]
 
		- roomList_lb.addItem(room.getName() + " (" + room.getUserCount() + ")", room.getId())
  
	- }
 
	- roomList_lb.sortItemsBy("label", "ASC")
 
	-  
 
	- // Join the default room
 
	- this.autoJoin()
 
 - }
  
            The first line makes sure that no item is present in the listbox. 
              Then we proceed by iterating through the roomList 
              array and we add each room name to the listbox (plase note that 
              the label is built by joining the room name and the user count for 
              that room). 
            Once the list is populated we can sort it in ascending alphabetical
              order. 
            Just like we did in the other tutorials we call the autoJoin() 
              method to automagically join the default room. 
             
              NOTE: 
              using the autoJoin() method is not mandatory but it is usually easier, 
              if you always need to bring the "just-arrived" users in 
              a default room. Also the autoJoin() method works 
              only if you have defined an autoJoin room in the zone, if none was 
              defined the call will fail. 
 
             
              [ UPDATING THE ROOM STATUS ] 
              Now that we have a complete list of rooms with the number of users
              for each of them how do we know
            when something changes? What happens if two users exit one room? 
            SmartFoxServer will send you notices of these changes, so all we 
              need to do is writing the appropriate handler for the onUserCountChange 
              event. 
            - smartfox.onUserCountChange = function(roomObj)
 
- {
 
	- updateRoomStatus(roomObj.getId())
  
- }
  
            Every time the event is fired the server passes a Room object
              that represents the room in which the change occured. 
              We have setup a simple function called updateRoomStatus 
              that will take care of changing the label in the room list component. 
            - function updateRoomStatus(roomId)
 
- {
 
	- var room = smartfox.roomList[roomId]
 
- var newLabel = room.name + " (" + room.getUserCount() + ")"
 
	- for (i=0; i < roomList_lb.getLength(); i++)
 
	- {
 
		- var item = roomList_lb.getItemAt(i)
 
- if (roomId == item.data)
 
		- {
 
			- roomList_lb.replaceItemAt(i, newLabel, item.data)
 
			- break;
  
		- }
  
	- }
  
- }
  
            The function takes the id of the room and loops through the list 
              box items until it finds the right item.Then it changes its label 
              updating the user count. 
            This technique should feel familiar to you at this point. 
             
              [ JOINING ANOTHER ROOM ] 
              At the very beginning of the code you will find these lines: 
            - //----------------------------------------------------------
 
- // Setup components callback functions
 
- //----------------------------------------------------------
 
- roomList_lb.setChangeHandler("changeRoom")
 
- userList_lb.setChangeHandler("userSelected")
  
            They set the name of the function to call when an item in the list 
              component is clicked. We'll concentrate on the changeRoom() method 
              for now: 
            - function changeRoom()
 
- {
 
	- var item = roomList_lb.getSelectedItem()
 
	  -  
 
	  - // new Room id
 
	- var newRoom = item.data
 
- if (newRoom != smartfox.activeRoomId)
 
	- {
 
		- // Check if new room is password protected 
 
		- var priv = smartfox.getRoom(newRoom).isPrivate()
 
- if (priv)
 
		- {
 
			- // Save newroom as _global for later use
 
			- _global.newRoom = newRoom
 
- showWindow("passwordWindow")
 
			 
		- }
 
		- else
 
		- {
 
			- // Pass the room id
 
			- smartfox.joinRoom(item.data)
  
		- }
  
	- }
  
- }
  
            The code checks that the room we've selected is different from 
              the one we're currently in, and it uses a SmartFoxClient property 
              that we haven't met yet: activeRoomId. This property 
              always holds the id of the last room we've joined. 
            Another important check we have to do is controlling if the room
              is password protected. 
            - var priv = smartfox.getRoom(newRoom).isPrivate()
  
            The getRoom(id) method returns a Room 
              object. The isPrivate() is a Room method: 
              it returns a boolean (true = password needed, false = no password). 
            If the room has no access restrictions we can join it by simply
              using smartfox.joinRoom() and passing the room id to it. 
            - smartfox.joinRoom(item.data)
  
            If the room needs a password we need to do some extra operations: 
            1) save the id of the room we want join somewhere for later use
              (_global.newRoom = newRoom) 
              2) show a dialog box and wait for user input (link to prev article) 
              3) finally send the login and password: smartfox.joinRoom(_global.newRoom,
              pwd) 
            Once the password is submitted the dialog box will call the loginProtectedRoom() 
              method in the main timeline: 
            - function loginProtectedRoom(pwd)
 
- {
 
	- hideWindow("passwordWindow")
 
	- smartfox.joinRoom(_global.newRoom, pwd)
  
- }
  
            which in turn sends the previously saved room Id and the password. 
             
              NOTE: 
              We have used the joinRoom() method with one argument for rooms
              with no
              passwords and with two arguments when a password is needed. To
              tell the truth the full set of arguments is this: 
            - joinRoom = function(newRoom, pword, dontLeave, oldRoom)
  
            SmartFoxServer allows a user to be present in more than one room 
              at a time. This can be useful for complex applications where you 
              need more advanced user interaction. However to keep things simple 
              the joinRoom method leaves the current room by 
              default before entering a new one as this is the most common behaviour 
              for most applications. 
              If you need to stay in one room while joining a new one you can 
              pass the dontLeave parameter as true. 
              One more thing about the newRoom argument. You can both pass the 
              room Id or the room name as first parameter. 
               
              Now that we have sent our joinRoom request 
              we should be prepared to receive complaints by the server. 
              For example the server may generate an error if the room we're trying 
              to join is already full. Antoher error could be generated if the 
              password sent is wrong. 
            The onJoinRoomError is responsible of handling 
              such event:  
            - smartfox.onJoinRoomError = function(errorMsg)
 
- {
 
	- var win = showWindow("errorWindow") 
 
	- win.errorMsg.text = errorMsg
 
	-  
 
	- // Put the selected room in the combo box back to its old value
 
	- resetRoomSelected(smartfox.activeRoomId)
  
- }
  
            The first two lines will show an error window and the text box
              inside the dialog box will show the error message passed by the
              server. 
              The next line invokes the resetRoomSelected(): 
              this is a little "trick" that we use to restore the selected 
              item in the room list component if the joinRoom request fails. 
             That's all for the first part of our "Advanced Chat" 
              application. 
               
               
              See you in the next article. 
            Lapo 
             |