import java.awt.event.*; import javax.swing.*; import com.genlogic.*; ////////////////////////////////////////////////////////////////////////// public class GlgProcessDemo extends GlgJBean implements ActionListener { ////////////////////////////////////////////////////////////////////////// // The main demo class ////////////////////////////////////////////////////////////////////////// static final long serialVersionUID = 0; // Constants static final int UpdateSpeed = 100, // ms SOLVENT_FLOW = 0, STEAM_FLOW = 1, COOLING_FLOW = 2, WATER_FLOW = 3; static final double PROCESS_SPEED = 0.25, HEATER_LEVEL_SPEED = 0.05, WATER_LEVEL_SPEED = 0.02, VALVE_CHANGE_SPEED = 0.05, STEAM_VALVE_CHANGE_SPEED = 0.05; // Variables boolean IsReady = false, AntiAliasing = true, ShowDynamics = true, ShowFlow = true, Show3D = true, // Initial setting WaterAlarm = false, HeaterAlarm = false; int ProcessCounter = 0, heater_high = 0, heater_low = 0, water_high = 0, water_low = 0, steam_high = 0, steam_low = 0, cooling_high = 0, cooling_low = 0; double SolventValve = 0.85, SteamValve = 1., CoolingValve = 0.8, WaterValve = 0.4, SolventFlow = 0., SteamFlow = 0., CoolingFlow = 0., WaterFlow = 0., OutFlow = 3495., SteamTemperature = 0., HeaterTemperature = 0., BeforePreHeaterTemperature = 0., PreHeaterTemperature = 0., AfterPreHeaterTemperature = 0., CoolingTemperature = 0., HeaterPressure = 0., HeaterLevel = 0.5, WaterLevel = 0.1; Timer timer = null; ////////////////////////////////////////////////////////////////////////// public GlgProcessDemo() { super(); SetDResource( "$config/GlgSwingUsage", 1. ); SetDResource( "$config/GlgAntiAliasing", AntiAliasing ? 1. : 0. ); } ////////////////////////////////////////////////////////////////////////// // Starts updates ////////////////////////////////////////////////////////////////////////// public void ReadyCallback() { if( GetJavaLog() ) PrintToJavaConsole( "Debug: Ready\n" ); super.ReadyCallback(); if( timer == null ) { timer = new Timer( 50, this ); timer.start(); } IsReady = true; } ////////////////////////////////////////////////////////////////////////// // For use as a stand-alone java demo ////////////////////////////////////////////////////////////////////////// public static void main( final String arg[] ) { SwingUtilities. invokeLater( new Runnable(){ public void run() { Main( arg ); } } ); } ////////////////////////////////////////////////////////////////////////// public static void Main( final String arg[] ) { class DemoQuit extends WindowAdapter { public void windowClosing( WindowEvent e ) { System.exit( 0 ); } } JFrame frame = new JFrame(); frame.setResizable( true ); frame.setSize( 700, 600 ); frame.setLocation( 20, 20 ); GlgProcessDemo process = new GlgProcessDemo(); frame.getContentPane().add( process ); frame.addWindowListener( new DemoQuit() ); frame.setVisible( true ); // Setting the viewport triggers the ReadyCallback which starts // updates process.SetViewport( GlgObject.LoadWidget( "process2.glg", GlgObject.FILE ) ); } ////////////////////////////////////////////////////////////////////////// // Recalculates new values for the process simulation model ////////////////////////////////////////////////////////////////////////// public void IterateProcess() { if( !IsReady || !ShowDynamics ) return; SteamTemperature += ( SteamValve - 0.6 ) * 2 * PROCESS_SPEED; SteamTemperature = PutInRange( SteamTemperature, 0., 1. ); HeaterTemperature += ( SteamTemperature - HeaterTemperature * HeaterLevel ) * PROCESS_SPEED; HeaterTemperature = PutInRange( HeaterTemperature, 0., 1. ); BeforePreHeaterTemperature += ( 1.5 * HeaterTemperature - BeforePreHeaterTemperature ) * PROCESS_SPEED; BeforePreHeaterTemperature = PutInRange( BeforePreHeaterTemperature, 0., 1. ); PreHeaterTemperature += ( BeforePreHeaterTemperature - PreHeaterTemperature ) * PROCESS_SPEED; PreHeaterTemperature = PutInRange( PreHeaterTemperature, 0., 1. ); AfterPreHeaterTemperature += ( 0.9 * HeaterTemperature - AfterPreHeaterTemperature ) * PROCESS_SPEED ; AfterPreHeaterTemperature = PutInRange( AfterPreHeaterTemperature, 0., 1. ); CoolingTemperature += ( AfterPreHeaterTemperature - CoolingTemperature - CoolingValve ) * PROCESS_SPEED; CoolingTemperature = PutInRange( CoolingTemperature, 0., 1. ); OutFlow = SolventValve * 3495.; HeaterLevel += ( SolventValve - 0.75 ) * HEATER_LEVEL_SPEED; HeaterLevel = PutInRange( HeaterLevel, 0., 1. ); // Inversed WaterLevel += ( 0.5 - WaterValve ) * WATER_LEVEL_SPEED; WaterLevel = PutInRange( WaterLevel, 0., 1. ); if( HeaterLevel > 0.9 || heater_high != 0 ) { heater_high = LugVar( heater_high, 10 ); SolventValve -= VALVE_CHANGE_SPEED; } else if( HeaterLevel < 0.45 || heater_low != 0 ) { heater_low = LugVar( heater_low, 10 ); SolventValve += VALVE_CHANGE_SPEED; } SolventValve = PutInRange( SolventValve, 0., 1. ); // Inversed if( WaterLevel > 0.2 || water_high != 0 ) { water_high = LugVar( water_high, 10 ); WaterValve += VALVE_CHANGE_SPEED; } else if( WaterLevel < 0.05 || water_low != 0 ) { water_low = LugVar( water_low, 10 ); WaterValve -= VALVE_CHANGE_SPEED; } WaterValve = PutInRange( WaterValve, 0., 1. ); if( SteamTemperature > 0.9 || steam_high != 0 ) { LugVar( steam_high, 20 ); SteamValve -= STEAM_VALVE_CHANGE_SPEED; } else if( SteamTemperature < 0.2 || steam_low != 0 ) { LugVar( steam_low, 20 ); SteamValve += STEAM_VALVE_CHANGE_SPEED; } SteamValve = PutInRange( SteamValve, 0., 1. ); if( CoolingTemperature > 0.7 || cooling_high != 0 ) { LugVar( cooling_high, 10 ); CoolingValve += VALVE_CHANGE_SPEED; } else if( CoolingTemperature < 0.3 || cooling_low != 0 ) { LugVar( cooling_low, 10 ); CoolingValve -= VALVE_CHANGE_SPEED; } CoolingValve = PutInRange( CoolingValve, 0., 1. ); HeaterPressure = HeaterLevel * ( HeaterTemperature + 1. ) / 2.; HeaterPressure = PutInRange( HeaterPressure, 0., 1. ); HeaterAlarm = ( HeaterLevel < 0.45 || HeaterLevel > 0.9 ); WaterAlarm = ( WaterLevel > 0.2 || WaterLevel < 0.05 ); UpdateProcess(); if( timer != null ) timer.start(); } ////////////////////////////////////////////////////////////////////////// // Injects the new recalculated values into the drawing ////////////////////////////////////////////////////////////////////////// public void UpdateProcess() { if( !IsReady ) return; if( GetJavaLog() ) PrintToJavaConsole( "Debug: UpdateProcess\n" ); SetDResource( "SolventValve/Angle", SolventValve ); SetDResource( "SteamValve/Angle", SteamValve ); SetDResource( "CoolingValve/Angle", CoolingValve ); SetDResource( "WaterValve/Angle", WaterValve ); if( ShowFlow ) { SetDResource( "SolventFlow", GetFlow( SOLVENT_FLOW ) ); SetDResource( "SteamFlow", GetFlow( STEAM_FLOW ) ); SetDResource( "CoolingFlow", GetFlow( COOLING_FLOW ) ); SetDResource( "WaterFlow", GetFlow( WATER_FLOW ) ); SetDResource( "OutFlow", OutFlow ); } SetDResource( "Heater/SteamTemperature", SteamTemperature ); SetDResource( "Heater/HeaterTemperature", HeaterTemperature ); SetDResource( "BeforePreHeaterTemperature", BeforePreHeaterTemperature ); SetDResource( "PreHeaterTemperature", PreHeaterTemperature ); SetDResource( "AfterPreHeaterTemperature", AfterPreHeaterTemperature ); SetDResource( "CoolingTemperature", CoolingTemperature ); SetDResource( "Heater/HeaterLevel", HeaterLevel ); SetDResource( "WaterSeparator/WaterLevel", WaterLevel ); SetDResource( "HeaterAlarm", HeaterAlarm ? 1. : 0 ); SetDResource( "WaterAlarm", WaterAlarm ? 1. : 0 ); SetDResource( "Graph/DataGroup/EntryPoint", HeaterTemperature ); SetDResource( "PressureGauge/Value", 5. * HeaterPressure ); Update(); } ////////////////////////////////////////////////////////////////////////// // Selection callback to handle mouse interaction ////////////////////////////////////////////////////////////////////////// public void SelectCallback( GlgObject vp, Object[] name_array, int button ) { double visibility, increment; String name; super.SelectCallback( vp, name_array, button ); if( name_array == null ) return; if( button == 1 ) increment = 1.; else increment = -1.; for( int i=0; ( name = (String) name_array[i] ) != null; ++i ) { if( name.equals( "SolventValve" ) ) { SolventValve += 0.2 * increment; SolventValve = PutInRange( SolventValve, 0., 1. ); SetDResource( "SolventValve/Angle", SolventValve ); break; } else if( name.equals( "SteamValve" ) ) { SteamValve += 0.2 * increment; SteamValve = PutInRange( SteamValve, 0., 1. ); SetDResource( "SteamValve/Angle", SteamValve ); break; } else if( name.equals( "CoolingValve" ) ) { CoolingValve += 0.2 * increment; CoolingValve = PutInRange( CoolingValve, 0., 1. ); SetDResource( "CoolingValve/Angle", CoolingValve ); break; } else if( name.equals( "WaterValve" ) ) { WaterValve += 0.2 * increment; WaterValve = PutInRange( WaterValve, 0., 1. ); SetDResource( "WaterValve/Angle", WaterValve ); break; } else if( name.indexOf( "Heater" ) == 0 || name.indexOf( "PressureGauge" ) == 0 ) { visibility = GetDResource( "PressureGauge/Visibility" ); SetDResource( "PressureGauge/Visibility", visibility == 0. ? 1. : 0. ); break; } } Update(); } ////////////////////////////////////////////////////////////////////////// // Recalculates the line type values used to simulate liquid flow. ////////////////////////////////////////////////////////////////////////// double GetFlow( int type ) { if( type == SOLVENT_FLOW ) return SolventFlow = GetFlowValue( SolventFlow, SolventValve ); else if( type == STEAM_FLOW ) return SteamFlow = GetFlowValue( SteamFlow, SteamValve ); else if( type == COOLING_FLOW ) return CoolingFlow = GetFlowValue( CoolingFlow, CoolingValve ); else if( type == WATER_FLOW ) return WaterFlow = GetFlowValue( WaterFlow, WaterValve ); else return 0.; } ////////////////////////////////////////////////////////////////////////// // Recalculates the line type values used to simulate liquid flow based // on the previous line type value and a flow speed defined by the // valve opening. // Parameters: // state - last value of the line type // valve - current valve opening ////////////////////////////////////////////////////////////////////////// double GetFlowValue( double state, double valve ) { int value, update_interval; if( valve == 0 ) value = 0; else { if( state == 0. ) value = 24; else { // Skip a few intervals to have variable speed. update_interval = 5 - (int) ( ( valve + 0.1 ) * 5. ); update_interval = Math.max( 0, update_interval ); update_interval = Math.min( 5, update_interval ); if( update_interval == 0 || ( ProcessCounter % update_interval ) == 0 ) { value = ((int) state) + 32; if( ( value % 32 % 24 ) != 0 ) value = 24; } else value = (int) state; // No change } } return value; } ////////////////////////////////////////////////////////////////////////// // Helps to implement lug behavior ////////////////////////////////////////////////////////////////////////// int LugVar( int variable, int lug ) { if( variable != 0 ) return --variable; else return lug; } ////////////////////////////////////////////////////////////////////////// double PutInRange( double variable, double low, double high ) { if( variable < low ) return low; else if( variable > high ) return high; else return variable; } ////////////////////////////////////////////////////////////////////////// public void ToggleDynamics() { ShowDynamics = !ShowDynamics; } ////////////////////////////////////////////////////////////////////////// public void ToggleDrawing() { if( !IsReady ) return; Show3D = !Show3D; ReloadDrawing(); } ////////////////////////////////////////////////////////////////////////// public void ToggleAntiAliasing() { if( !IsReady ) return; AntiAliasing = !AntiAliasing; SetDResource( "$config/GlgAntiAliasing", AntiAliasing ? 1. : 0. ); // Reload with new AntiAliasing setting ReloadDrawing(); } ////////////////////////////////////////////////////////////////////////// void ReloadDrawing() { StopUpdates(); IsReady = false; ShowDynamics = true; // Unset previous drawing to force re-loading even if the drawing is the // same. SetDrawingURL( null ); SetDrawingURL( Show3D ? "process2.glg" : "process.glg" ); } ////////////////////////////////////////////////////////////////////////// // Stops updates when used as an applet. ////////////////////////////////////////////////////////////////////////// public void stop() { StopUpdates(); IsReady = false; super.stop(); } ////////////////////////////////////////////////////////////////////////// void StopUpdates() { if( timer != null ) { timer.stop(); timer = null; } } ////////////////////////////////////////////////////////////////////////// // ActionListener method to use the bean as update timer's ActionListener. ////////////////////////////////////////////////////////////////////////// public void actionPerformed( ActionEvent e ) { if( timer != null ) IterateProcess(); } ////////////////////////////////////////////////////////////////////////// // Inner class for a Runnable interface. // Provides an interface between JavaScript and Java: invokes applet's // methods in a synchronous way as required by Swing. ////////////////////////////////////////////////////////////////////////// class GlgBeanRunnable implements Runnable { GlgProcessDemo bean; String request_name; int value; public GlgBeanRunnable( GlgProcessDemo bean_p, String request_name_p, int value_p ) { bean = bean_p; request_name = request_name_p; value = value_p; } public void run() { if( request_name.equals( "ToggleDynamics" ) ) bean.ToggleDynamics(); else if( request_name.equals( "ToggleDrawing" ) ) bean.ToggleDrawing(); else if( request_name.equals( "ToggleAntiAliasing" ) ) bean.ToggleAntiAliasing(); else PrintToJavaConsole( "Invalid request name: " + request_name + "\n" ); } } ////////////////////////////////////////////////////////////////////////// // Provides an interface between JavaScript and Java: invokes applet's // methods in a synchronous way as required by Swing. ////////////////////////////////////////////////////////////////////////// public void SendRequest( String request_name, int value ) { GlgBeanRunnable runnable = new GlgBeanRunnable( this, request_name, value ); SwingUtilities.invokeLater( runnable ); } }