001package jmri.jmrix.lenz;
002
003import java.io.DataInputStream;
004import java.io.DataOutputStream;
005import javax.annotation.OverridingMethodsMustInvokeSuper;
006
007/**
008 * Abstract base for classes representing an XNet communications port
009 *
010 * @author Bob Jacobsen Copyright (C) 2001, 2008
011 * @author Paul Bender Copyright (C) 2004,2010,2014
012 */
013public class XNetStreamPortController extends jmri.jmrix.AbstractStreamPortController implements XNetPortController {
014
015    private boolean timeSlot = true;
016
017    public XNetStreamPortController(DataInputStream in, DataOutputStream out, String pname) {
018        super(new XNetSystemConnectionMemo(), in, out, pname);
019    }
020
021    public XNetStreamPortController() {
022        super(new XNetSystemConnectionMemo());
023    }
024
025    @Override
026    public void configure() {
027        // connect to a packetizing traffic controller
028        XNetTrafficController packets = new XNetPacketizer(new LenzCommandStation());
029        packets.connectPort(this);
030
031        this.getSystemConnectionMemo().setXNetTrafficController(packets);
032
033        new XNetInitializationManager()
034                .memo(this.getSystemConnectionMemo())
035                .setDefaults()
036                .setTimeout(30000)
037                .versionCheck()
038                .init();
039    }
040
041    @Override
042    public XNetSystemConnectionMemo getSystemConnectionMemo() {
043        return (XNetSystemConnectionMemo) super.getSystemConnectionMemo();
044    }
045
046    /**
047     * Check that this object is ready to operate. This is a question of
048     * configuration, not transient hardware status.
049     */
050    @Override
051    public boolean status() {
052        return (getInputStream()!=null && getOutputStream()!=null);
053    }
054
055    /**
056     * Can the port accept additional characters?
057     */
058    @Override
059    @OverridingMethodsMustInvokeSuper
060    public boolean okToSend() {
061        return ( status() && hasTimeSlot() );
062    }
063
064    /**
065     * Indicate whether the Command Station is currently providing a timeslot to this
066     * port controller.
067     *
068     * @return true if the Command Station is currently providing a timeslot.
069     */
070    @Override
071    public boolean hasTimeSlot(){
072        return timeSlot;
073    }
074
075    /**
076     * Set a variable indicating whether or not the command station is
077     * providing a timeslot.
078     * <p>
079     * This method should be called with the paramter set to false if
080     * a "Command Station No Longer Providing a timeslot for communications"
081     * (01 05 04) is received.
082     * <p>
083     * This method should be called with the parameter set to true if
084     * a "Command Station is providing a timeslot for communications again."
085     * (01 07 06) is received.
086     *
087     * @param timeslot true if a timeslot is being sent, false otherwise.
088     */
089    @Override
090    public void setTimeSlot(boolean timeslot){
091       timeSlot = timeslot;
092    }  
093
094    /**
095     * We need a way to say if the output buffer is empty or full this should
096     * only be set to false by external processes.
097     */
098    @Override
099    synchronized public void setOutputBufferEmpty(boolean s) {
100    }
101
102}