// (c) MIT 2003.  All rights reserved.

// -*-Mode: Java-*- 
// $Id: SpeechToSketchAgent.java,v 1.2 2003/03/06 00:40:43 moltmans Exp $
// SpeechToSketchAgent.java -- 
// Author: Michael Oltmans <moltmans@ai.mit.edu> 
// Created: <Thu Jul 29 15:54:39 1999> 
// Time-stamp: <2000-03-04 14:13:03 moltmans> 
package rec.agent;

import java.util.*;
import java.rmi.*;

import rec.util.*;
import rec.sys.*;
import speech.*;
import speech.tools.*;
import rec.speech.*;

/**
 * This is the agent that sends recognized utterances to the
 * rec.agent.SketchAgent.  From there the SketchAgent can add
 * utterance widgets to the rec system.
 **/
public class SpeechToSketchAgent extends SpeechAgent
  implements SpeechToSketch
{

  //  protected Sketch m_Sketch;
  protected AppGrammar m_DictGram;
  protected Hashtable m_Grammars;


  public SpeechToSketchAgent( ) throws RemoteException
  {
    //    m_Sketch = (Sketch)reliesOn( "rec.agent.Sketch" );
    m_Grammars = new Hashtable( );

    m_DictGram = loadGrammar( "rec.agent.Empty" );

    // this is a hack. there should be a systematic way of doing this
    // without reaching into the guts of listen...  but for now it
    // saves having to say "computer, stay awake"
    Listen l = Listen.getListen();
    l.requestWakeUp();
    l.stayAwake();
  }

  /**
   * @param grammar Should be a string with the full package specifier
   * of the grammar.
   */
  public void addGrammar( String grammar ) throws RemoteException
  {
    Console.writeln( "Loading: " + grammar );
    boolean exists = m_Grammars.containsKey( grammar );
    Assert.note( !exists, "Grammar already present: " + grammar );
   
    if ( exists )
      return;

    AppGrammar ag = loadGrammar( grammar );
    m_Grammars.put( grammar, ag );
    makeAlwaysActive( ag );
  }
  
  public void removeGrammar( String grammar ) throws RemoteException
  {
    boolean exists = m_Grammars.containsKey( grammar );
    Assert.note( exists, "Grammar not found: " + grammar );
    
    if ( ! exists )
      return;

    AppGrammar ag = (AppGrammar)m_Grammars.get( grammar );
    ag.deactivate();
    //    ag.shutdown();
    m_Grammars.remove( grammar );
  }

  public void removeAllGrammars() throws RemoteException
  {
    Iterator it = new HashSet( m_Grammars.keySet() ).iterator();
    while( it.hasNext() ){
      String grammar = (String)it.next();
      removeGrammar( grammar );
    }
  }
  
  public void activateGrammar( String grammar ) throws RemoteException 
  {
    boolean exists = m_Grammars.containsKey( grammar );
    Assert.note( exists, "Grammar not found: " + grammar );
    
    if ( ! exists )
      return;
    AppGrammar ag = (AppGrammar)m_Grammars.get( grammar );
    ag.activate( );
  }
  
  public void deactivateGrammar( String grammar ) throws RemoteException
  {
    boolean exists = m_Grammars.containsKey( grammar );
    Assert.note( exists, "Grammar not found: " + grammar );
    
    if ( ! exists )
      return;
    AppGrammar ag = (AppGrammar)m_Grammars.get( grammar );
    ag.deactivate( );
  }
  

  public String getDictation( ) throws RemoteException 
  {
    // need to find some way to get ahold of an AppGrammar before we
    // can do this...
    //    Assert.error( "NO DICTATION CAPABILITIES YET.  COME BACK TOMORROW." );
    //    return "NO DICTATION CAPABILITIES YET.  COME BACK TOMORROW.";

    return m_DictGram.getDictation( );
  }

  public void sayPhrase( String phrase ) throws RemoteException
  {
    m_DictGram.say( phrase );
  }

  /**
   * This sends all utterances from all grammars off to the sketch
   * system which will add the utterance to the surface and let the
   * recognizers/reasoners/resolvers handle it.
   */
  public void acceptedTagsResult( Tag tags ) throws RemoteException
  {
    Console.writeln( "Sending tags to SketchAgent: " + tags );
    Sketch sketch = (Sketch)reliesOn( "rec.agent.Sketch" );
    sketch.addUtterance( new WSpeechUtterance( tags ) );
  }
    
}



