TextMeshPro issues with input field

Hi everyone !
I have another issue to report.
I am trying to create a TMPro Inputfield from script and not from Unity Editor. I created each GameObjects as the editor does (TextMeshPro - InputField, Text Area, Placeholder, and Text) with the correct MonoBehaviours and hierarchy.
Thing is the GameObject “TextMeshPro - InputField Input Caret” is never created during the execution and we can not see caret and selection when inputfield is selected. I tried to create it myseflf but I can not link it to the TMP_InputField behaviour.

Edit : I am using Unity 5.6.6f2, and Text Mesh Pro 1.2.2

Here is my own component Start method which create an InputField :

 private void Start()
   {
      RectTransform inputFieldTransform = gameObject.GetComponent<RectTransform>();

      Image image = gameObject.AddComponent<Image>();
      image.color = Color.white;
      image.raycastTarget = true;
      image.type = Image.Type.Sliced;
      image.fillCenter = true;

      TMP_InputField inputField = gameObject.AddComponent<TMP_InputField>();

      GameObject textAreaObject = new GameObject("Text Area");
      RectTransform textAreaTransform = textAreaObject.AddComponent<RectTransform>();
      textAreaTransform.anchorMin = new Vector2(0, 0);
      textAreaTransform.anchorMax = new Vector2(1, 1);
      textAreaTransform.pivot = new Vector2(0.5f, 0.5f);
      textAreaTransform.sizeDelta = new Vector2(0, 0);
      textAreaObject.AddComponent<RectMask2D>();
      textAreaTransform.SetParent(inputFieldTransform, false);

      GameObject placeholderObject = new GameObject("Placeholder");
      RectTransform placeholderTransform = placeholderObject.AddComponent<RectTransform>();

      TextMeshProUGUI placeholderText = placeholderObject.AddComponent<TextMeshProUGUI>();
      placeholderText.text = "Enter text...";
      placeholderText.fontSize = 40;
      placeholderText.alignment = TextAlignmentOptions.TopLeft;
      placeholderText.color = Color.grey;

      placeholderTransform.anchorMin = new Vector2(0, 0);
      placeholderTransform.anchorMax = new Vector2(1, 1);
      placeholderTransform.pivot = new Vector2(0.5f, 0.5f);
      placeholderTransform.sizeDelta = new Vector2(0, 0);
      placeholderTransform.SetParent(textAreaTransform, false);

      GameObject textObject = new GameObject("Text");
      RectTransform textTransform = textObject.AddComponent<RectTransform>();

      TextMeshProUGUI textText = textObject.AddComponent<TextMeshProUGUI>();
      textText.text = "Enter text...";
      textText.fontSize = 40;
      textText.alignment = TextAlignmentOptions.TopLeft;
      textText.color = Color.black;

      textTransform.anchorMin = new Vector2(0, 0);
      textTransform.anchorMax = new Vector2(1, 1);
      textTransform.pivot = new Vector2(0.5f, 0.5f);
      textTransform.sizeDelta = new Vector2(0, 0);
      textTransform.SetParent(textAreaTransform, false);

      inputField.interactable = true;
      inputField.transition = Selectable.Transition.ColorTint;
      inputField.targetGraphic = image;
      inputField.textViewport = textAreaTransform;
      inputField.textComponent = textText;
      inputField.placeholder = placeholderText;
      inputField.fontAsset = Resources.Load<TMP_FontAsset>("Fonts & Materials/LiberationSans SDF");

      //GameObject caret = new GameObject("TextMeshPro - InputField Input Caret");
      //caret.transform.SetParent(textAreaObject.transform, false);
      //caret.AddComponent<TMP_SelectionCaret>();
      //caret.AddComponent<LayoutElement>().ignoreLayout = true;
   }

Am I missing something ?
Thank you all,
Arthur

I think the easier approach is to create it in editor (right click in hierarchy) and then make a prefab out of it. Then, just instantiate that prefab in runtime. You can add that prefab in resources folder, and then acess it through code via Resources.Load<TMP_InputField>(“Prefab_path”)

Thank you for your reply, but in my project I really can’t instantiate a prefab. I tried your solution in a little project and works fine, but I can’t do that in my own project where all my gameObjects and Monobehaviour are instantiated from script.

The release notes for the Unity version 2019.1.0a11 contains this line “Universal Windows Platform: Fix InputField text selection so it works on Windows 10 touch-enabled devices (1002834)” and links to THIS issue in the IssueTracker.

So we were super excited and tried it out but apparently it’s only fixed in the Unity Inputfield, not in the TextMesh Pro Inputfield. Do you know if this fix is coming to TextMesh Pro, @Stephan_B ?

Anyway, I’m going to create a new bugreport with a new repro-project because these are things that are important for our project. As I probably mentioned before a big part of our application is the Text Editor.

This is only valid for 2019.1. Try the following changes in the TMP_InputField.cs

Add the following private field around line 292

private bool m_TouchKeyboardAllowsInPlaceEditing = false;

Make the following change in the following function around line 1075.

private bool InPlaceEditing()
{
     return !TouchScreenKeyboard.isSupported || m_TouchKeyboardAllowsInPlaceEditing;
}

Modify the function ActivateInputFieldInternal() around line 3214.

private void ActivateInputFieldInternal()
{
    if (EventSystem.current == null)
        return;
    if (EventSystem.current.currentSelectedGameObject != gameObject)
        EventSystem.current.SetSelectedGameObject(gameObject);
    if (TouchScreenKeyboard.isSupported)
    {
        if (Input.touchSupported)
        {
            TouchScreenKeyboard.hideInput = shouldHideMobileInput;
        }

        // Revise the following two sections of code 
        m_Keyboard = (inputType == InputType.Password) ?
            TouchScreenKeyboard.Open(m_Text, keyboardType, false, multiLine, true, false, "", characterLimit) :
            TouchScreenKeyboard.Open(m_Text, keyboardType, inputType == InputType.AutoCorrect, multiLine, false, false, "", characterLimit);

        // Cache the value of isInPlaceEditingAllowed, because on UWP this involves calling into native code
        // The value only needs to be updated once when the TouchKeyboard is opened.
        m_TouchKeyboardAllowsInPlaceEditing = TouchScreenKeyboard.isInPlaceEditingAllowed;
        
        // Mimics OnFocus but as mobile doesn't properly support select all
        // just set it to the end of the text (where it would move when typing starts)
        MoveTextEnd(false);
    }
    else
    {
        Input.imeCompositionMode = IMECompositionMode.On;
        OnFocus();
    }
    //m_StringPosition = m_StringSelectPosition = 0;
    //m_CaretPosition = m_CaretSelectPosition = 0;
    m_AllowInput = true;
    m_OriginalText = text;
    m_WasCanceled = false;
    SetCaretVisible();
    UpdateLabel();
}

Let me know if this works as expected on your end.

@Stephan_B , I have implemented the code you suggested. This makes it possible to insert text on the caret position but only when I move the caret by using the Arrow-keys on the keyboard. Clicking the inputfield does nothing, the caret stays at the end of the line.

I made a bugreport yesterday which includes a repro-project and an UWP build, do you have access to those? The case number is 1108599.

I’ll try taking a look at the bug report tomorrow.

If you have time, I would be curious to know if this works as expected on the target device when using the UI Input Field as opposed to the TMP Input Field.

The Unity Inputfield works as expected. Clicking within a line moves the caret to that position and typing text inserts it at that position. Thanks for your time. I really appreciate it.

@Stephan_B have you had any time to check out the bugreport?

I am currently working on the Input Field and should be able to look into this later today / tonight.

1 Like

I’m having this exact same issue. Only the initial text is selectable/scrollable etc, once you add some new text which pushes content down, you can’t select or edit anything outside that initial box.

Is there any workaround that anyone knows of? Or am I doing something wrong?

Hi @Stephan_B ,

Just checking if this one on your radar

Cheers and thanks for all the awesome work on TMP

1 Like

Disable the GameObject that you attached the TMP_InputField component to (this.gameObject in your example), and the re-enable it after all of the script have been attached.

My guess is that it needs everything to be present before executing. Disabling the GameObject disables all the scripts attached to it.

It does cause another problem: the entered text will not be visible if “too much” text is entered. At least in my case.

I didn’t test it with your code, but I have been doing something similar, and that worked for me.

checkman’s solution worked for me when creating a TMP Input Field from scratch in C#:

go_input.SetActive(false);
go_input.SetActive(true);

Caret now shows up fine. Thanks - saved me a lot of hassle!

xnfx4c
Caret position is not changing on click pos instead it changes caret pos when i try to change it from keyboards additional input field even though mobile input is disabled

Have you tried to disable “OnFocus - Select All”? I’ve tested it, sometimes it isn’t taking it as a ‘click’, but as a drag as if you’re selecting the text…

no need anymore my project got canceled anyway :slight_smile:

Hey just wondering what the latest in in-place select cursor and copy/paste is for touch / mobile

Hi everyone,

I’ve stumbled upon a minor nitpick and the closest I can come to an explanation is issue #1 described in this post.
In my project I’ve designed a user interface which includes a TMP_InputField. When the user has entered at least one character, everything is fine. Unfortunately, while the InputField is still empty the caret is too big and spans beyond the line.

7243520--872453--TMP_InputFieldCaret_User.PNG
7243520--872450--TMP_InputFieldCaret_Placeholder.PNG

I’m using Unity 2020.1.14 with TMP version 3.0.6. The text settings are identical for placeholder and normal text (except for the placeholder being italic). Is it possible the caret tries to match the last character and since it can’t find one in the empty InputField, it defaults to something doesn’t match the text settings? If so, how can I fix that?

Thank you in advance!

Kind regards,

Karrzun

1 Like

Bumping this up.
Having the same issue, looking for a way to solve it through anchoring but cant find a way.
@Stephan_B , anyone?

Edit: figured this out thanks to my collegue.
Just put content size fitter on the most inner text component, veritcal fit - preferred size. This will make it’s rect transform always include all the text, and since caret’s rect transform always mimics this components rect transform, the carret will always include all the text too.

Edit2:
My first proposed soulution does not work as expected : ).
Luckily I found out there is an textMeshPro example for this, just import text mesh pro examples and find scrollable input text example, i think it was example 24 not sure.
Use this, it works.

1 Like