001package jmri.jmrix.zimo;
002
003import static jmri.jmrix.zimo.Mx1Message.ACKREP1;
004
005import jmri.JmriException;
006import jmri.managers.AbstractPowerManager;
007
008/**
009 * PowerManager implementation for controlling layout power.
010 *
011 * @author Bob Jacobsen Copyright (C) 2001
012  *
013 * Adapted by Sip Bosch for use with zimo Mx-1
014 *
015 */
016public class Mx1PowerManager extends AbstractPowerManager<Mx1SystemConnectionMemo> implements Mx1Listener {
017
018    Mx1TrafficController tc = null;
019
020    public Mx1PowerManager(Mx1SystemConnectionMemo memo) {
021        super(memo);
022        // connect to the TrafficManager
023        this.tc = memo.getMx1TrafficController();
024        tc.addMx1Listener(~0, this);
025
026        try {
027            setPower(OFF);
028        } catch (JmriException e) {
029        }
030    }
031
032    @Override
033    public void setPower(int v) throws JmriException {
034        int old = power;
035        power = UNKNOWN;
036        if (tc.getProtocol() == Mx1Packetizer.ASCII) {
037            checkTC();
038            if (v == ON) {
039                // send GPON
040                Mx1Message m = new Mx1Message(3);
041                m.setElement(0, 0x53);
042                m.setElement(1, 0x45);
043                tc.sendMx1Message(m, this);
044            } else if (v == OFF) {
045                // send GPOFF
046                Mx1Message m = new Mx1Message(3);
047                m.setElement(0, 0x53);
048                m.setElement(1, 0x41);
049                tc.sendMx1Message(m, this);
050            }
051            // request status
052            Mx1Message m = new Mx1Message(2);
053            m.setElement(0, 0x5A);
054            tc.sendMx1Message(m, this);
055        } else {
056            if (v == ON) {
057                tc.sendMx1Message(Mx1Message.setPowerOn(), this);
058            } else if (v == OFF) {
059                tc.sendMx1Message(Mx1Message.setPowerOff(), this);
060            }
061            if (memo.getConnectionType() == Mx1SystemConnectionMemo.MXULF) {
062                //MXULF doesn't return the correct status of the track power, so we have to assume it has been set                
063                power = v;
064                firePowerPropertyChange(old, power);
065            } 
066        }
067    }
068
069    // to free resources when no longer used
070    @Override
071    public void dispose() throws JmriException {
072        tc.removeMx1Listener(~0, this);
073        tc = null;
074    }
075
076    private void checkTC() throws JmriException {
077        if (tc == null) {
078            throw new JmriException("attempt to use PowerManager after dispose");
079        }
080    }
081
082    // to listen for status changes from net
083    @Override
084    public void message(Mx1Message m) {
085        int old = power;
086        if (tc.getProtocol() == Mx1Packetizer.ASCII) {
087            if (m.getElement(0) == 0x5a) {
088                if ((m.getElement(2) & 0x02) == 0x02) {
089                    power = ON;
090                } else {
091                    power = OFF;
092                }
093            } else if (m.getMessageType() == ACKREP1 && m.getPrimaryMessage() == Mx1Message.TRACKCTL) {
094                if ((m.getElement(4) & 0x02) == 0x02) {
095                    power = OFF;
096                } else {
097                    power = ON;
098                }
099            }
100        } else {
101            if (m.getMessageType() == ACKREP1 && m.getPrimaryMessage() == Mx1Message.TRACKCTL) {
102                if ((m.getElement(4) & 0x02) == 0x02) {
103                    power = ON;
104                } else {
105                    power = OFF;
106                }
107            }
108        }
109        firePowerPropertyChange(old, power); 
110    }
111}
112
113
114