struct SPresetTimetableEntry { instanceeditable var time : SSimpleGameTime; instanceeditable var useTime : Bool; var arrayPosition : Int32; var entryID : Uint32; } struct SmartHouseConfiguration { instanceeditable var enableInteraction : Bool; instanceeditable var factName : CName; } class SmartHouseController extends MasterController { public const override function GetPS() : SmartHouseControllerPS { return ( ( SmartHouseControllerPS )( GetBasePS() ) ); } } class SmartHouseControllerPS extends MasterControllerPS { default m_deviceName = "LocKey#15648"; default m_tweakDBRecord = T"Devices.SmartHouse"; default m_tweakDBDescriptionRecord = T"device_descriptions.SmartHouse"; protected var m_timetable : array< SPresetTimetableEntry >; protected inlined var m_activePreset : SmartHousePreset; protected const instanceeditable inlined var m_availablePresets : array< SmartHousePreset >; protected instanceeditable var m_smartHouseCustomization : SmartHouseConfiguration; protected var m_callbackID : Uint32; protected event OnInstantiated() { super.OnInstantiated(); } protected override function Initialize() { super.Initialize(); } protected override function GameAttached() { InitializePreset(); } public function GetCustomizationFact() : CName { return m_smartHouseCustomization.factName; } public function RegisterFactCallback() { if( m_smartHouseCustomization.enableInteraction && IsNameValid( m_smartHouseCustomization.factName ) ) { m_callbackID = GameInstance.GetQuestsSystem( GetGameInstance() ).RegisterEntity( m_smartHouseCustomization.factName, PersistentID.ExtractEntityID( GetID() ) ); } } public function UnregisterFactCallback() { if( m_smartHouseCustomization.enableInteraction && IsNameValid( m_smartHouseCustomization.factName ) ) { GameInstance.GetQuestsSystem( GetGameInstance() ).UnregisterEntity( m_smartHouseCustomization.factName, m_callbackID ); } } public override function GetActions( out outActions : array< DeviceAction >, context : GetActionsContext ) : Bool { var i : Int32; var fact : Int32; super.GetActions( outActions, context ); for( i = 0; i < m_availablePresets.Size(); i += 1 ) { if( ( m_activePreset != m_availablePresets[ i ] ) && PresetAction.IsAvailable( this ) ) { outActions.PushBack( ActionPreset( m_availablePresets[ i ] ) ); } } fact = GameInstance.GetQuestsSystem( GetGameInstance() ).GetFact( m_smartHouseCustomization.factName ); if( m_smartHouseCustomization.enableInteraction && ( fact == 0 ) ) { outActions.PushBack( ActionOpenInteriorManager() ); } SetActionIllegality( outActions, m_illegalActions.regularActions ); return true; } protected function ActionOpenInteriorManager() : OpenInteriorManager { var action : OpenInteriorManager; action = new OpenInteriorManager; action.SetUp( this ); action.SetProperties(); action.AddDeviceName( m_deviceName ); action.CreateActionWidgetPackage(); return action; } public virtual function OnOpenInteriorManager( evt : OpenInteriorManager ) : EntityNotificationType { UseNotifier( evt ); SetFactValue( GetGameInstance(), m_smartHouseCustomization.factName, 1 ); return EntityNotificationType.SendThisEventToEntity; } protected function ActionPreset( preset : SmartHousePreset ) : PresetAction { var action : PresetAction; action = new PresetAction; action.clearanceLevel = DefaultActionsParametersHolder.GetToggleOnClearance(); action.SetUp( this ); action.SetProperties( preset ); action.AddDeviceName( m_deviceName ); action.CreateActionWidgetPackage(); return action; } public virtual function OnPresetAction( evt : PresetAction ) : EntityNotificationType { UseNotifier( evt ); m_activePreset = evt.GetPreset(); m_activePreset.ExecutePresetActions( GetImmediateSlaves() ); return EntityNotificationType.SendThisEventToEntity; } public function ActivatePreset( i : Int32 ) { m_activePreset = m_availablePresets[ i ]; if( GetActiveTimeTableEntry() == i ) { m_activePreset.ExecutePresetActions( GetImmediateSlaves() ); } } public function QuestForcePreset( preset : CName ) { var i : Int32; for( i = 0; i < m_availablePresets.Size(); i += 1 ) { if( m_availablePresets[ i ].GetClassName() == preset ) { m_activePreset = m_availablePresets[ i ]; m_activePreset.ExecutePresetActions( GetImmediateSlaves() ); NotifyParents(); break; } } } protected function InitializePreset() { var i : Int32; var currentTimetable : SPresetTimetableEntry; for( i = 0; i < m_availablePresets.Size(); i += 1 ) { currentTimetable = m_availablePresets[ i ].GetTimeTable(); if( m_timetable.Size() == 0 ) { if( currentTimetable.useTime ) { currentTimetable.arrayPosition = i; m_timetable.PushBack( currentTimetable ); } } else { CheckTimetable( currentTimetable, i ); } } InitializeTimetable(); } protected function InitializeTimetable() { var i : Int32; var activeEntry : Int32; var evt : PresetTimetableEvent; var timeout : GameTime; var entryTime : GameTime; var timeSystem : TimeSystem; timeSystem = GameInstance.GetTimeSystem( GetGameInstance() ); activeEntry = GetActiveTimeTableEntry(); for( i = 0; i < m_timetable.Size(); i += 1 ) { evt = new PresetTimetableEvent; evt.arrayPosition = m_timetable[ i ].arrayPosition; entryTime = MakeTime( m_timetable[ i ].time ); timeout = GameTime.MakeGameTime( 0, 24, 0, 0 ); m_timetable[ i ].entryID = timeSystem.RegisterIntervalListener( GetOwnerEntityWeak(), evt, entryTime, timeout, -1 ); if( i == activeEntry ) { GetOwnerEntityWeak().QueueEvent( evt ); } } } public function UninitializeTimetable() { var i : Int32; for( i = 0; i < m_timetable.Size(); i += 1 ) { GameInstance.GetTimeSystem( GetGameInstance() ).UnregisterListener( m_timetable[ i ].entryID ); } } protected const function GetActiveTimeTableEntry() : Int32 { var currentTime : GameTime; var entryTime : GameTime; var time : GameTime; var storedtime : GameTime; var i : Int32; var id : Int32; var wasTimeStored : Bool; currentTime = GetCurrentTime(); for( i = 0; i < m_timetable.Size(); i += 1 ) { entryTime = MakeTime( m_timetable[ i ].time ); if( currentTime < entryTime ) { time = ( GameTime.MakeGameTime( 0, 24, 0, 0 ) - entryTime ) + currentTime; } else { time = currentTime - entryTime; } if( ( time < storedtime ) || !( wasTimeStored ) ) { wasTimeStored = true; storedtime = time; id = i; } } return id; } protected function CheckTimetable( newTable : SPresetTimetableEntry, arrayPos : Int32 ) { var i : Int32; var sameHour : Bool; for( i = 0; i < m_timetable.Size(); i += 1 ) { if( newTable.useTime ) { if( m_timetable[ i ].time.hours == newTable.time.hours ) { sameHour = true; } } } if( !( sameHour ) ) { newTable.arrayPosition = arrayPos; m_timetable.PushBack( newTable ); } } protected const function GetCurrentTime() : GameTime { var currentTime : GameTime; currentTime = GameInstance.GetTimeSystem( GetGameInstance() ).GetGameTime(); return GameTime.MakeGameTime( 0, GameTime.Hours( currentTime ), GameTime.Minutes( currentTime ), GameTime.Seconds( currentTime ) ); } protected const function MakeTime( time : SSimpleGameTime ) : GameTime { return GameTime.MakeGameTime( 0, time.hours, time.minutes, time.seconds ); } public override function GetDeviceWidget( const context : ref< GetActionsContext > ) : SDeviceWidgetPackage { var widgetData : SDeviceWidgetPackage; widgetData = super.GetDeviceWidget( context ); return widgetData; } protected override function GetInkWidgetTweakDBID( const context : ref< GetActionsContext > ) : TweakDBID { if( !( IsUserAuthorized( context.processInitiatorObject.GetEntityID() ) ) && !( context.ignoresAuthorization ) ) { return super.GetInkWidgetTweakDBID( context ); } else { return T"DevicesUIDefinitions.SmartHouseDeviceWidget"; } } }