1*bf47c682SAndroid Build Coastguard Worker /* 2*bf47c682SAndroid Build Coastguard Worker * Copyright (C) 2016 The Android Open Source Project 3*bf47c682SAndroid Build Coastguard Worker * 4*bf47c682SAndroid Build Coastguard Worker * Licensed under the Apache License, Version 2.0 (the "License"); 5*bf47c682SAndroid Build Coastguard Worker * you may not use this file except in compliance with the License. 6*bf47c682SAndroid Build Coastguard Worker * You may obtain a copy of the License at 7*bf47c682SAndroid Build Coastguard Worker * 8*bf47c682SAndroid Build Coastguard Worker * http://www.apache.org/licenses/LICENSE-2.0 9*bf47c682SAndroid Build Coastguard Worker * 10*bf47c682SAndroid Build Coastguard Worker * Unless required by applicable law or agreed to in writing, software 11*bf47c682SAndroid Build Coastguard Worker * distributed under the License is distributed on an "AS IS" BASIS, 12*bf47c682SAndroid Build Coastguard Worker * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13*bf47c682SAndroid Build Coastguard Worker * See the License for the specific language governing permissions and 14*bf47c682SAndroid Build Coastguard Worker * limitations under the License. 15*bf47c682SAndroid Build Coastguard Worker */ 16*bf47c682SAndroid Build Coastguard Worker 17*bf47c682SAndroid Build Coastguard Worker #import <Foundation/Foundation.h> 18*bf47c682SAndroid Build Coastguard Worker 19*bf47c682SAndroid Build Coastguard Worker #import "MIDIClient.h" 20*bf47c682SAndroid Build Coastguard Worker #import "MIDIMessage.h" 21*bf47c682SAndroid Build Coastguard Worker 22*bf47c682SAndroid Build Coastguard Worker extern NSString * const WALTClientErrorDomain; 23*bf47c682SAndroid Build Coastguard Worker 24*bf47c682SAndroid Build Coastguard Worker /** A reasonable timeout to use when reading from the WALT. */ 25*bf47c682SAndroid Build Coastguard Worker extern const NSTimeInterval kWALTReadTimeout; 26*bf47c682SAndroid Build Coastguard Worker 27*bf47c682SAndroid Build Coastguard Worker typedef NS_ENUM(MIDIByte, WALTCommand) { 28*bf47c682SAndroid Build Coastguard Worker WALTDelayedPingCommand = 'D', // Ping with a delay 29*bf47c682SAndroid Build Coastguard Worker WALTResetCommand = 'F', // Reset all vars 30*bf47c682SAndroid Build Coastguard Worker WALTSendSyncCommand = 'I', // Send some digits for clock sync 31*bf47c682SAndroid Build Coastguard Worker WALTPingCommand = 'P', // Ping with a single byte 32*bf47c682SAndroid Build Coastguard Worker WALTVersionCommand = 'V', // Determine WALT's firmware version 33*bf47c682SAndroid Build Coastguard Worker WALTReadoutSyncCommand = 'R', // Read out sync times 34*bf47c682SAndroid Build Coastguard Worker WALTGShockCommand = 'G', // Send last shock time and watch for another 35*bf47c682SAndroid Build Coastguard Worker WALTTimeCommand = 'T', // Current time 36*bf47c682SAndroid Build Coastguard Worker WALTZeroSyncCommand = 'Z', // Initial zero 37*bf47c682SAndroid Build Coastguard Worker WALTScreenOnCommand = 'C', // Send a message on screen color change 38*bf47c682SAndroid Build Coastguard Worker WALTScreenOffCommand = 'c', 39*bf47c682SAndroid Build Coastguard Worker WALTSendLastScreenCommand = 'E', // Send info about last screen color change 40*bf47c682SAndroid Build Coastguard Worker WALTBrightnessCurveCommand = 'U', // Probe screen for brightness vs time curve 41*bf47c682SAndroid Build Coastguard Worker WALTLaserOnCommand = 'L', // Send messages on state change of the laser 42*bf47c682SAndroid Build Coastguard Worker WALTLaserOffCommand = 'l', 43*bf47c682SAndroid Build Coastguard Worker WALTSendLastLaserCommand = 'J', 44*bf47c682SAndroid Build Coastguard Worker WALTAudioCommand = 'A', // Start watching for signal on audio out line 45*bf47c682SAndroid Build Coastguard Worker WALTBeepCommand = 'B', // Generate a tone into the mic and send timestamp 46*bf47c682SAndroid Build Coastguard Worker WALTBeepStopCommand = 'S', // Stop generating tone 47*bf47c682SAndroid Build Coastguard Worker WALTMIDICommand = 'M', // Start listening for a MIDI message 48*bf47c682SAndroid Build Coastguard Worker WALTNoteCommand = 'N', // Generate a MIDI NoteOn message 49*bf47c682SAndroid Build Coastguard Worker }; 50*bf47c682SAndroid Build Coastguard Worker 51*bf47c682SAndroid Build Coastguard Worker typedef struct { 52*bf47c682SAndroid Build Coastguard Worker char tag; 53*bf47c682SAndroid Build Coastguard Worker NSTimeInterval t; 54*bf47c682SAndroid Build Coastguard Worker int value; 55*bf47c682SAndroid Build Coastguard Worker unsigned int count; 56*bf47c682SAndroid Build Coastguard Worker } WALTTrigger; 57*bf47c682SAndroid Build Coastguard Worker 58*bf47c682SAndroid Build Coastguard Worker /** 59*bf47c682SAndroid Build Coastguard Worker * A client for a WALT device. 60*bf47c682SAndroid Build Coastguard Worker * 61*bf47c682SAndroid Build Coastguard Worker * The client will automatically try to connect to any available WALT device, and monitor the system 62*bf47c682SAndroid Build Coastguard Worker * for device connections/disconnections. Users should observe the "connected" key to be notified of 63*bf47c682SAndroid Build Coastguard Worker * connection changes. 64*bf47c682SAndroid Build Coastguard Worker * 65*bf47c682SAndroid Build Coastguard Worker * Most commands produce a corresponding response from the WALT. The -sendCommand:error: method 66*bf47c682SAndroid Build Coastguard Worker * should be used to send the command, and -readResponse used to collect the response. 67*bf47c682SAndroid Build Coastguard Worker */ 68*bf47c682SAndroid Build Coastguard Worker @interface WALTClient : NSObject <MIDIClientDelegate> 69*bf47c682SAndroid Build Coastguard Worker @property (readonly, nonatomic, getter=isConnected) BOOL connected; 70*bf47c682SAndroid Build Coastguard Worker 71*bf47c682SAndroid Build Coastguard Worker /** 72*bf47c682SAndroid Build Coastguard Worker * Returns the base time of the WALT device. 73*bf47c682SAndroid Build Coastguard Worker * 74*bf47c682SAndroid Build Coastguard Worker * The time value is an adjusted version of -currentTime. 75*bf47c682SAndroid Build Coastguard Worker */ 76*bf47c682SAndroid Build Coastguard Worker @property (readonly, nonatomic) NSTimeInterval baseTime; 77*bf47c682SAndroid Build Coastguard Worker 78*bf47c682SAndroid Build Coastguard Worker /** Returns the number of seconds the system has been awake since it was last restarted. */ 79*bf47c682SAndroid Build Coastguard Worker @property (readonly, nonatomic) NSTimeInterval currentTime; 80*bf47c682SAndroid Build Coastguard Worker 81*bf47c682SAndroid Build Coastguard Worker /** Initialises the client and attempts to connect to any available WALT device. */ 82*bf47c682SAndroid Build Coastguard Worker - (instancetype)initWithError:(NSError **)error; 83*bf47c682SAndroid Build Coastguard Worker 84*bf47c682SAndroid Build Coastguard Worker /** Sends a command to the WALT. */ 85*bf47c682SAndroid Build Coastguard Worker - (BOOL)sendCommand:(WALTCommand)command error:(NSError **)error; 86*bf47c682SAndroid Build Coastguard Worker 87*bf47c682SAndroid Build Coastguard Worker /** Reads a response from the WALT, blocking up to timeout until one becomes available. */ 88*bf47c682SAndroid Build Coastguard Worker - (NSData *)readResponseWithTimeout:(NSTimeInterval)timeout; 89*bf47c682SAndroid Build Coastguard Worker 90*bf47c682SAndroid Build Coastguard Worker /** 91*bf47c682SAndroid Build Coastguard Worker * Reads a trigger response from the WALT. 92*bf47c682SAndroid Build Coastguard Worker * 93*bf47c682SAndroid Build Coastguard Worker * If an error occurs, the trigger's tag will be '\0'. 94*bf47c682SAndroid Build Coastguard Worker */ 95*bf47c682SAndroid Build Coastguard Worker - (WALTTrigger)readTriggerWithTimeout:(NSTimeInterval)timeout; 96*bf47c682SAndroid Build Coastguard Worker 97*bf47c682SAndroid Build Coastguard Worker /** Returns YES if the response data contains a valid acknowledgement for a command. */ 98*bf47c682SAndroid Build Coastguard Worker - (BOOL)checkResponse:(NSData *)response forCommand:(WALTCommand)command; 99*bf47c682SAndroid Build Coastguard Worker 100*bf47c682SAndroid Build Coastguard Worker /** Forces a complete clock synchronisation with the WALT. */ 101*bf47c682SAndroid Build Coastguard Worker - (BOOL)syncClocksWithError:(NSError **)error; 102*bf47c682SAndroid Build Coastguard Worker 103*bf47c682SAndroid Build Coastguard Worker /** Refreshes the min/max error synchronisation bounds. */ 104*bf47c682SAndroid Build Coastguard Worker - (BOOL)updateSyncBoundsWithError:(NSError **)error; 105*bf47c682SAndroid Build Coastguard Worker 106*bf47c682SAndroid Build Coastguard Worker @property (readonly, nonatomic) int64_t minError; 107*bf47c682SAndroid Build Coastguard Worker @property (readonly, nonatomic) int64_t maxError; 108*bf47c682SAndroid Build Coastguard Worker 109*bf47c682SAndroid Build Coastguard Worker /** 110*bf47c682SAndroid Build Coastguard Worker * Confirms the connection with the WALT (by setting -isConnected). 111*bf47c682SAndroid Build Coastguard Worker * 112*bf47c682SAndroid Build Coastguard Worker * Note that this method will only return NO if there is an error in the connection process. The 113*bf47c682SAndroid Build Coastguard Worker * absence of a device is not such an error. 114*bf47c682SAndroid Build Coastguard Worker */ 115*bf47c682SAndroid Build Coastguard Worker - (BOOL)checkConnectionWithError:(NSError **)error; 116*bf47c682SAndroid Build Coastguard Worker 117*bf47c682SAndroid Build Coastguard Worker /** Returns the time of the last shock detected by the WALT. */ 118*bf47c682SAndroid Build Coastguard Worker - (NSTimeInterval)lastShockTimeWithError:(NSError **)error; 119*bf47c682SAndroid Build Coastguard Worker @end 120