001package jmri.jmrix.can.cbus; 002 003import java.util.ArrayList; 004import java.util.List; 005import javax.annotation.Nonnull; 006 007import jmri.AddressedProgrammer; 008import jmri.ProgListener; 009import jmri.ProgrammerException; 010import jmri.ProgrammingMode; 011import jmri.jmrix.can.CanReply; 012 013/** 014 * Provide an Ops Mode Programmer via a wrapper what works with the CBUS command 015 * station object. 016 * <p> 017 * Functionally, this just creates packets to send via the command station. 018 * 019 * @see jmri.Programmer 020 * @author Andrew Crosland Copyright (C) 2009 021 */ 022public class CbusDccOpsModeProgrammer extends CbusDccProgrammer implements AddressedProgrammer { 023 024 int mAddress; 025 boolean mLongAddr; 026 027 public CbusDccOpsModeProgrammer(int pAddress, boolean pLongAddr, jmri.jmrix.can.TrafficController tc) { 028 super(tc); 029 mAddress = pAddress; 030 mLongAddr = pLongAddr; 031 } 032 033 /** 034 * {@inheritDoc} 035 * 036 * Forward a write request to an ops-mode write operation 037 */ 038 @Override 039 synchronized public void writeCV(String CVname, int val, ProgListener p) throws ProgrammerException { 040 final int CV = Integer.parseInt(CVname); 041 log.debug("ops mode write CV={} val={}", CV, val); 042 043 // record state. COMMANDSENT is just waiting for a reply... 044 useProgrammer(p); 045 _progRead = false; 046 progState = COMMANDSENT; 047 _val = val; 048 _cv = CV; 049 050 // send the programming command 051 tc.sendCanMessage(CbusMessage.getOpsModeWriteCV(mAddress, mLongAddr, CV, val, tc.getCanid()), this); 052 notifyProgListenerEnd(_val, jmri.ProgListener.OK); 053 } 054 055 /** 056 * {@inheritDoc} 057 */ 058 @Override 059 synchronized public void readCV(String CVname, ProgListener p) throws ProgrammerException { 060 log.error("readCV {} not available for MERG CBUS, a query to track would return all locos",CVname); 061 throw new ProgrammerException(); 062 } 063 064 /** 065 * {@inheritDoc} 066 */ 067 @Override 068 synchronized public void confirmCV(String CV, int val, ProgListener p) throws ProgrammerException { 069 log.error("confirmCV {} not available for MERG CBUS, a query to track would return all locos",CV); 070 throw new ProgrammerException(); 071 } 072 073 /** 074 * {@inheritDoc} 075 * 076 * Types implemented here. 077 */ 078 @Override 079 @Nonnull 080 public List<ProgrammingMode> getSupportedModes() { 081 List<ProgrammingMode> ret = new ArrayList<>(1); 082 ret.add(ProgrammingMode.OPSBYTEMODE); 083 return ret; 084 } 085 086 /** 087 * {@inheritDoc} 088 */ 089 @Override 090 synchronized public void reply(CanReply m) { 091 // We will not see any replies 092 } 093 094 /** 095 * {@inheritDoc} 096 * 097 * Can this ops-mode programmer read back values? 098 * 099 * @return always false 100 */ 101 @Override 102 public boolean getCanRead() { 103 return false; 104 } 105 106 /** 107 * {@inheritDoc} 108 */ 109 @Override 110 public boolean getLongAddress() { 111 return mLongAddr; 112 } 113 114 /** 115 * {@inheritDoc} 116 */ 117 @Override 118 public int getAddressNumber() { 119 return mAddress; 120 } 121 122 /** 123 * {@inheritDoc} 124 */ 125 @Override 126 public String getAddress() { 127 return "" + getAddressNumber() + " " + getLongAddress(); 128 } 129 130 /** 131 * Ops-mode programming doesn't put the command station in programming mode, 132 * so we don't have to send an exit-programming command at end. Therefore, 133 * this routine does nothing except to replace the parent routine that does 134 * something. 135 */ 136 void cleanup() { 137 } 138 139 private final static org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(CbusDccOpsModeProgrammer.class); 140}