
/*
 * weinre is available under *either* the terms of the modified BSD license *or* the
 * MIT License (2008). See http://opensource.org/licenses/alphabetical for full text.
 * 
 * Copyright (c) 2010, 2011 IBM Corporation
 */

requireClass ../common/Callback
requireClass ../common/Weinre

requireClass ./WeinreExtraTargetEventsImpl

//-----------------------------------------------------------------------------
class WeinreClientEventsImpl(client)
    this.client = client

//-----------------------------------------------------------------------------
init
    var titleNotConnected    = "weinre: target not connected"
    var titleConnectedPrefix = "weinre: "
    
    document.title = titleNotConnected
     
//-----------------------------------------------------------------------------
method clientRegistered(clientDescription)
    if (this.client.uiAvailable()) {
        WebInspector.panels.remote.addClient(clientDescription)
    }

//-----------------------------------------------------------------------------
method targetRegistered(targetDescription)
    if (this.client.uiAvailable()) {
        WebInspector.panels.remote.addTarget(targetDescription)
    }
    
    if (!Weinre.client.autoConnect()) return
    if (!Weinre.messageDispatcher) return
    
    Weinre.WeinreClientCommands.connectTarget(Weinre.messageDispatcher.channel, targetDescription.channel)

//-----------------------------------------------------------------------------
method clientUnregistered(/*int*/ clientChannel)
    if (this.client.uiAvailable()) {
        WebInspector.panels.remote.removeClient(clientChannel)
    }

//-----------------------------------------------------------------------------
method targetUnregistered(/*int*/ targetChannel)
    if (this.client.uiAvailable()) {
        WebInspector.panels.remote.removeTarget(targetChannel)
    }

//-----------------------------------------------------------------------------
method connectionCreated(/*int*/ clientChannel, /*int*/ targetChannel)
    if (this.client.uiAvailable()) {
        WebInspector.panels.remote.setClientState(clientChannel, "connected") 
        WebInspector.panels.remote.setTargetState(targetChannel, "connected")
    }
    
    if (clientChannel != Weinre.messageDispatcher.channel) return

    WebInspector.panels.elements.reset()
    WebInspector.panels.timeline._clearPanel()
    WebInspector.panels.resources.reset()
    
    var target = WebInspector.panels.remote.getTarget(targetChannel)
    document.title = titleConnectedPrefix + target.url
    
    WebInspector.inspectedURLChanged(target.url)

    Weinre.WeinreExtraClientCommands.getDatabases(function(databaseRecords) {
        WeinreExtraTargetEventsImpl.addDatabaseRecords(databaseRecords)
    })
    
//-----------------------------------------------------------------------------
method connectionDestroyed(/*int*/ clientChannel, /*int*/ targetChannel)

    if (this.client.uiAvailable()) {
        WebInspector.panels.remote.setClientState(clientChannel, "not-connected") 
        WebInspector.panels.remote.setTargetState(targetChannel, "not-connected")
    }
    
    if (clientChannel != Weinre.messageDispatcher.channel) return

    document.title = titleNotConnected
    
    if (!Weinre.client.autoConnect()) return
    if (!this.client.uiAvailable()) return
    
    var nextTargetChannel = WebInspector.panels.remote.getNewestTargetChannel(targetChannel)
    if (!nextTargetChannel) return
    
    Weinre.WeinreClientCommands.connectTarget(Weinre.messageDispatcher.channel, nextTargetChannel)
    Weinre.logInfo("autoconnecting to " + nextTargetChannel)

//-----------------------------------------------------------------------------
method sendCallback(/*int*/ callbackId, /*any*/ result)
    Callback.invoke(callbackId, result)

//-----------------------------------------------------------------------------
method serverProperties(/*any*/ properties)
    if (this.client.uiAvailable()) {
        WebInspector.panels.remote.setServerProperties(properties)
    }
