diff --git a/component/signal_dcxh.go b/component/signal_dcxh.go new file mode 100644 index 0000000..1a3da24 --- /dev/null +++ b/component/signal_dcxh.go @@ -0,0 +1,28 @@ +package component + +import "joylink.club/ecs" + +// SignalDCXHElectronic 电路状态:信号机DCXH(蓝-白) 调车信号机 +type SignalDCXHElectronic struct { + //灯丝继电器,true-吸合 + DCXH_DJ *ecs.Entry + //调车信号继电器,true-吸合 + DCXH_DXJ *ecs.Entry +} + +// SignalDCXHFilament 信号机DCXH 灯丝状态 +type SignalDCXHFilament struct { + // 物理白灯,true-灯丝正常 + Bf bool + // 物理蓝灯,true-灯丝正常 + Af bool + // 物理白灯,true-亮 + B bool + // 物理蓝灯,true-亮 + A bool +} + +var ( + SignalDCXHElectronicType = ecs.NewComponentType[SignalDCXHElectronic]() + SignalDCXHFilamentType = ecs.NewComponentType[SignalDCXHFilament]() +) diff --git a/entity/signal.go b/entity/signal.go index 6657ed1..9a8937d 100644 --- a/entity/signal.go +++ b/entity/signal.go @@ -41,6 +41,9 @@ func LoadSignals(w ecs.World) error { } case consts.SIGNAL_JDXH: case consts.SIGNAL_DCXH: + if le := loadSignalDcxh(w, signal, signalEntry, elecs, data.EntityMap); le != nil { + return le + } case consts.SIGNAL_JCKXH: default: return fmt.Errorf("id=[%s]的信号机,无效组合类型[%s]", signal.Id(), group.Code()) diff --git a/entity/signal_dcxh.go b/entity/signal_dcxh.go new file mode 100644 index 0000000..1f458de --- /dev/null +++ b/entity/signal_dcxh.go @@ -0,0 +1,35 @@ +package entity + +import ( + "fmt" + "joylink.club/ecs" + "joylink.club/rtsssimulation/component" + "joylink.club/rtsssimulation/consts" + "joylink.club/rtsssimulation/repository" +) + +func loadSignalDcxh(w ecs.World, signal *repository.Signal, signalEntry *ecs.Entry, elecs []repository.IGroupedElectronicComponent, entityMap map[string]*ecs.Entry) error { + + if len(elecs) == 2 { //dcxh组合类型包含2个继电器 + signalEntry.AddComponent(component.SignalDCXHElectronicType) + signalEntry.AddComponent(component.SignalDCXHFilamentType) + // + elecState := &component.SignalDCXHElectronic{} + for _, elec := range elecs { + switch elec.Code() { + case consts.SIGNAL_DJ: + elecState.DCXH_DJ = NewRelayEntity(w, elec.(*repository.Relay), entityMap) + case consts.SIGNAL_DXJ: + elecState.DCXH_DXJ = NewRelayEntity(w, elec.(*repository.Relay), entityMap) + default: + return fmt.Errorf("id=[%s]的信号机dcxh,无效电子元器件名称[%s]", signal.Id(), elec.Code()) + } + } + // + component.SignalDCXHElectronicType.Set(signalEntry, elecState) + component.SignalDCXHFilamentType.Set(signalEntry, &component.SignalDCXHFilament{Bf: true, Af: true, B: false, A: false}) + } else { + return fmt.Errorf("id=[%s]的信号机dcxh,电子元器件数量须为2", signal.Id()) + } + return nil +} diff --git a/sys/bind.go b/sys/bind.go index 3a35a1d..3c213e2 100644 --- a/sys/bind.go +++ b/sys/bind.go @@ -18,5 +18,6 @@ func BindSystem(w ecs.World) { circuit_sys.NewSignal3XH1System(), circuit_sys.NewSignal3XH2System(), circuit_sys.NewSignal3XH3System(), - circuit_sys.NewSignal3XH4System()) + circuit_sys.NewSignal3XH4System(), + circuit_sys.NewSignalDCXHSystem()) } diff --git a/sys/circuit_sys/signal_dcxh.go b/sys/circuit_sys/signal_dcxh.go new file mode 100644 index 0000000..ed35edd --- /dev/null +++ b/sys/circuit_sys/signal_dcxh.go @@ -0,0 +1,51 @@ +package circuit_sys + +import ( + "github.com/yohamta/donburi/filter" + "joylink.club/ecs" + "joylink.club/rtsssimulation/component" +) + +type SignalDCXHSystem struct { + query *ecs.Query +} + +func NewSignalDCXHSystem() *SignalDCXHSystem { + return &SignalDCXHSystem{query: ecs.NewQuery(filter.Contains(component.SignalDCXHElectronicType, component.SignalDCXHFilamentType))} +} + +// Update world 执行 +func (s *SignalDCXHSystem) Update(w ecs.World) { + s.query.Each(w, func(e *ecs.Entry) { + state := component.SignalDCXHElectronicType.Get(e) + filament := component.SignalDCXHFilamentType.Get(e) + // + s.calculateA(state, filament) + s.calculateB(state, filament) + s.calculateDJ(state, filament) + }) + +} + +func (s *SignalDCXHSystem) calculateB(state *component.SignalDCXHElectronic, filament *component.SignalDCXHFilament) { + dxj := component.BitStateType.Get(state.DCXH_DXJ) + isB := filament.Bf && dxj.Val + filament.B = isB +} + +func (s *SignalDCXHSystem) calculateA(state *component.SignalDCXHElectronic, filament *component.SignalDCXHFilament) { + dxj := component.BitStateType.Get(state.DCXH_DXJ) + isA := filament.Af && !dxj.Val + filament.A = isA +} + +func (s *SignalDCXHSystem) calculateDJ(state *component.SignalDCXHElectronic, filament *component.SignalDCXHFilament) { + dxj := component.BitStateType.Get(state.DCXH_DXJ) + dj := component.BitStateType.Get(state.DCXH_DJ) + isDJ := filament.Bf && dxj.Val || filament.Af && !dxj.Val + if isDJ != dj.Val { + drive := component.RelayDriveType.Get(state.DCXH_DJ) + drive.Td = isDJ + drive.Xq = isDJ + } +}