Project: engagement_generation License: BSD Dependencies:
Used by:
None |
engagement_generation/src/edu/wpi/hri/gen/comm/BMLRealizer.javaGo to the documentation of this file.00001 /* 00002 * Software License Agreement (BSD License) 00003 * 00004 * Copyright (c) 2010, Worcester Polytechnic Institute 00005 * All rights reserved. 00006 * 00007 * Redistribution and use in source and binary forms, with or without 00008 * modification, are permitted provided that the following conditions 00009 * are met: 00010 * 00011 * * Redistributions of source code must retain the above copyright 00012 * notice, this list of conditions and the following disclaimer. 00013 * * Redistributions in binary form must reproduce the above 00014 * copyright notice, this list of conditions and the following 00015 * disclaimer in the documentation and/or other materials provided 00016 * with the distribution. 00017 * * Neither the name of Worcester Polytechnic Institute. nor the names 00018 * of its contributors may be used to endorse or promote products 00019 * derived from this software without specific prior written permission. 00020 * 00021 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 00022 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 00023 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 00024 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 00025 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 00026 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 00027 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 00028 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 00029 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 00030 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 00031 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 00032 * POSSIBILITY OF SUCH DAMAGE. 00033 */ 00034 package edu.wpi.hri.gen.comm; 00035 00036 import java.util.ArrayList; 00037 import java.util.List; 00038 00039 import ros.NodeHandle; 00040 import ros.RosException; 00041 import ros.ServiceClient; 00042 import ros.Subscriber; 00043 import ros.pkg.engagement_msgs.msg.BCOccurrence; 00044 import ros.pkg.bml_msgs.msg.BMLPerformance; 00045 import ros.pkg.bml_msgs.msg.Behavior; 00046 import ros.pkg.bml_msgs.msg.BehaviorResult; 00047 import ros.pkg.bml_msgs.msg.Flag; 00048 import ros.pkg.engagement_msgs.msg.HumanBackchannel; 00049 import ros.pkg.bml_srvs.srv.BMLRealization; 00050 import edu.wpi.hri.comm.MasterSpinner; 00051 import edu.wpi.hri.gen.ebml.EBMLList; 00052 import edu.wpi.hri.log.Logger; 00053 import edu.wpi.hri.log.Logger.Colors; 00054 import edu.wpi.hri.log.Logger.LoggerLevel; 00055 00063 public class BMLRealizer { 00064 00065 private final ServiceClient<BMLRealization.Request, BMLRealization.Response, BMLRealization> realizeSrv; 00066 private final Subscriber<BMLPerformance> performSub; 00067 private final Subscriber<HumanBackchannel> bcSub; 00068 private final Logger logger; 00069 private final MasterSpinner spinner; 00070 private List<BCOccurrence> backchannels; 00071 private Behavior currentBehavior; 00072 00088 public BMLRealizer(NodeHandle handle, MasterSpinner spin, Logger logger) 00089 throws RosException { 00090 this.logger = logger.sub(Colors.BML, "BML"); 00091 this.realizeSrv = handle.serviceClient("bml/realize", 00092 new BMLRealization()); 00093 this.performSub = handle.subscribe("bml/performing", 00094 new BMLPerformance(), new PerformanceCallback(), 100); 00095 this.bcSub = handle.subscribe("recognition/human/backchannel", 00096 new HumanBackchannel(), new BCSubscriber(), 100); 00097 00098 this.spinner = spin; 00099 this.backchannels = null; 00100 this.currentBehavior = null; 00101 this.logger.debug(LoggerLevel.INIT, "Created ..."); 00102 } 00103 00108 public void shutdown() { 00109 this.realizeSrv.shutdown(); 00110 this.performSub.shutdown(); 00111 this.bcSub.shutdown(); 00112 } 00113 00121 public Result sendBML(EBMLList list) { 00122 this.spinner.startNewMaster(); 00123 String bml = list.toBML(); 00124 // only allow one realization at a time 00125 synchronized (this) { 00126 // create the request object 00127 this.logger.debug(LoggerLevel.IO, "sending :" + bml); 00128 BMLRealization.Request req = new BMLRealization.Request(); 00129 req.bml = bml; 00130 00131 try { 00132 // create a list for backchannels to be placed in 00133 ArrayList<BCOccurrence> backs = new ArrayList<BCOccurrence>(); 00134 this.backchannels = backs; 00135 00136 // then call the realization service 00137 BMLRealization.Response res = this.realizeSrv.call(req); 00138 return new Result(res.success.value, res.behaviors, backs); 00139 } catch (RosException e) { 00140 this.logger.error("Could not call realization: " 00141 + e.getMessage()); 00142 } 00143 // something bad happened when calling the realization service 00144 return new Result(Flag.FAILURE, new ArrayList<BehaviorResult>(), 00145 new ArrayList<BCOccurrence>()); 00146 } 00147 } 00148 00156 public static class Result { 00157 public final byte success; 00158 public final ArrayList<BehaviorResult> behaviors; 00159 public final ArrayList<BCOccurrence> backchannels; 00160 00171 Result(byte success, ArrayList<BehaviorResult> behav, 00172 ArrayList<BCOccurrence> backs) { 00173 this.success = success; 00174 this.behaviors = behav; 00175 this.backchannels = backs; 00176 } 00177 } 00178 00185 private class PerformanceCallback implements 00186 Subscriber.Callback<BMLPerformance> { 00187 00188 @Override 00189 public void call(BMLPerformance msg) { 00190 logger.debug(LoggerLevel.IO, "performing " + msg.behavior.id + ":" 00191 + msg.behavior.synchPoint); 00192 currentBehavior = msg.behavior; 00193 } 00194 } 00195 00203 private class BCSubscriber implements Subscriber.Callback<HumanBackchannel> { 00204 00205 @Override 00206 public void call(HumanBackchannel msg) { 00207 if (currentBehavior != null) { 00208 logger.debug(LoggerLevel.POLICY_EXECUTION, 00209 "Backchannel occurred " + msg.actor.id + " at " 00210 + currentBehavior.id + ":" 00211 + currentBehavior.synchPoint); 00212 BCOccurrence bco = new BCOccurrence(); 00213 bco.behavior = currentBehavior; 00214 bco.actor.id = msg.actor.id; 00215 bco.result.value = Flag.BEGIN; 00216 backchannels.add(bco); 00217 } else { 00218 logger.warn("Backchannels should only occur during bml execution, something is wrong"); 00219 } 00220 } 00221 } 00222 } |