#if UNITY_EDITOR_OSX || UNITY_STANDALONE_OSX #define ZF_OSX #endif using System.Collections.Generic; using UnityEngine; namespace ZenFulcrum.EmbeddedBrowser { /// /// Helper class for IBrowserUI implementations for getting/generating keyboard events for sending to an IBrowserUI. /// public class KeyEvents { /** Fills up with key events as they happen. */ protected List keyEvents = new List(); /** Swaps with keyEvents on InputUpdate and is returned in the main getter. */ protected List keyEventsLast = new List(); /// /// After calling InputUpdate, contains the key events to send to the browser. /// public List Events { get { return keyEventsLast; } } /** List of keys Unity won't give us events for. So we have to poll. */ static readonly KeyCode[] keysToCheck = { #if ZF_OSX //On windows you get GUI events for ctrl, super, alt. On mac...you don't! KeyCode.LeftCommand, KeyCode.RightCommand, KeyCode.LeftControl, KeyCode.RightControl, KeyCode.LeftAlt, KeyCode.RightAlt, //KeyCode.CapsLock, unity refuses to inform us of this, so there's not much we can do #endif //Unity consistently doesn't send events for shift across all platforms. KeyCode.LeftShift, KeyCode.RightShift, }; /// /// Call once per frame before grabbing /// public void InputUpdate() { //Note: keyEvents gets filled in OnGUI as things happen. InputUpdate get called just before it's read. //To get the right events to the right place at the right time, swap the "double buffer" of key events. var tmp = keyEvents; keyEvents = keyEventsLast; keyEventsLast = tmp; keyEvents.Clear(); //Unity doesn't include events for some keys, so fake it by checking each frame. for (int i = 0; i < keysToCheck.Length; i++) { if (Input.GetKeyDown(keysToCheck[i])) { //Prepend down, postpend up. We don't know which happened first, but pressing //modifiers usually precedes other key presses and releasing tends to follow. keyEventsLast.Insert(0, new Event() { type = EventType.KeyDown, keyCode = keysToCheck[i] }); } else if (Input.GetKeyUp(keysToCheck[i])) { keyEventsLast.Add(new Event() { type = EventType.KeyUp, keyCode = keysToCheck[i] }); } } } /// /// Call this with any GUI events you get from Unity that you want to have passed to the browser. /// /// public void Feed(Event ev) { if (ev.type != EventType.KeyDown && ev.type != EventType.KeyUp) return; // if (ev.character != 0) Debug.Log("ev >>> " + ev.character); // else if (ev.type == EventType.KeyUp) Debug.Log("ev ^^^ " + ev.keyCode); // else if (ev.type == EventType.KeyDown) Debug.Log("ev vvv " + ev.keyCode); keyEvents.Add(new Event(ev)); } /// /// Injects a key press. Call Release laster to let go. /// If the key you are pressing represents a character this may not type that character. Use Type() instead. /// /// public void Press(KeyCode key) { keyEvents.Add(new Event { type = EventType.KeyDown, keyCode = key }); } public void Release(KeyCode key) { keyEvents.Add(new Event { type = EventType.KeyUp, keyCode = key }); } /// /// Types the given text in. THis does not simulate pressing each key and releasing it. /// /// public void Type(string text) { for (int i = 0; i < text.Length; i++) { //fixme: multibyte chars >16 bits keyEvents.Add(new Event { type = EventType.KeyDown, character = text[i], }); } } } }