// Copyright 2017 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

library fuchsia.ui.input;
using fuchsia.ui.input3;

enum KeyboardType {
    TEXT = 0;
    NUMBER = 1;
    PHONE = 2;
    DATETIME = 3;
};

enum InputMethodAction {
    UNSPECIFIED = 0;
    NONE = 1;
    GO = 2;
    SEARCH = 3;
    SEND = 4;
    NEXT = 5;
    DONE = 6;
    PREVIOUS = 7;
};

/// The current text, selection, and composing state for editing a run of text.
struct TextInputState {
    /// Current state revision to avoid race conditions.
    uint32 revision;

    /// The current text being edited.
    string text;

    /// The range of text that is currently selected.
    TextSelection selection;

    /// The range of text that is still being composed.
    TextRange composing;
};

/// A interface for interacting with a text input control.
protocol InputMethodEditor {
    SetKeyboardType(KeyboardType keyboard_type);
    SetState(TextInputState state);

    // DEPRECATED: Will be replaced with DispatchKey3
    InjectInput(InputEvent event);

    // Notify IME Service of a keyboard event. Will be migrated into
    // fuchsia.ui.input after fuchsia.ui.input cleanup.
    // TODO(fxbug.dev/68265)
    [Transitional]
    DispatchKey3(fuchsia.ui.input3.KeyEvent event) -> (bool handled);

    // TODO(fxbug.dev/26729): remove these in a later change, after PlatformView has been
    // switched over to open/close on the input_connection_ instead.
    Show();
    Hide();
};

/// An interface to receive information from `TextInputService`.
protocol InputMethodEditorClient {
    DidUpdateState(TextInputState state, InputEvent? event);
    OnAction(InputMethodAction action);
};
