Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

robinsonryan's avatar

Clearing the value of a text input when checkbox checked

I don't use Vue much because I'm usually on the backend of Laravel. But, I understand the basics. I am on a project that uses the Laravel, Jetstream, Inertia stack. I need a form submission to send the following data back to my app on the following format:

{
	medical: {
		arthritis: "", //null is also acceptable
		heart disease: "Some notes about heart disease condition",
		//.....more medical conditions
	}
}

or 

medical: {} //no medical conditions are sent in submission

I'm trying to build a form component that correctly gathers the data. Every condition has a checkbox and an text input for notes. The text input is disabled until the associated checkbox is checked. Once checked, the condition is added to the model as the key with an empty note as the value and the text input is enabled. If the user enters notes, the model is updated to reflect the notes as the value with the condition as the key.

If the user unchecks the checkbox, the condition and notes are removed from the model. The text input should be cleared. This is the part I can't get working.

The inputs are created in a v-for and added as a ref. But, as far as I can tell, I can't access the individual inputs in the ref because the conditionNotes.value returns and array and accessing conditionNotes.value[0] (or any valid [n]) just returns a string representation of the input, not a ref to the actual input.

I don't even know if this is the correct way to create the component in the first place, but below is what I have. Any suggestions are welcom. Here is a link to SFC Playground to see it working.

How can I clear the input?

<template>
    <div>
        <h2>Medical Condition</h2>
        <p>Is checked: {{ model.checked }}</p>
        <p>{{ model.medical }}</p>
        <div v-for="(value, key) in model.medicalCondition">
          <input type="checkbox" :id="key" :name="key" :value="key" @change="updateConditions">
          <input type="text"
                 :id="key + 'Notes'"
                 :condition="key"
                 ref="conditionNotes"
                 :disabled="!model.medicalCondition[key]"
                 @input="updateNote"
                 >
      		Condition: {{key}} Checked: {{value}}
      	</div>
    </div>
</template>
<script setup>
    import { reactive, ref } from 'vue';
    
    const conditionNotes = ref(null);
		    
    const model = reactive(
    {
        medical: {},
        checked: false,
      	medicalCondition: {
          'arthritis': false,
          'asthma': false,
          'high blood pressure' : false
        }
    });

    function updateConditions(e)
    {
        let value = e.target.value;
        if(e.target.checked)
        {
           model.medicalCondition[e.target.value] = true;
           model.medical[value] = {};
        } else {
          model.medicalCondition[e.target.value] = false;
          delete model.medical[value];
          
          //clear the input here
          //but I don't know how to access it
          console.log(conditionNotes.value); //outputs a object with the array of inputs
      		console.log(conditionNotes.value[0]); //outputs a string "<input type="text" ...>"
        }
    }

    function addNote(e)
    {
        model.medical.condition[e.target.value] = e.target.checked;
    }
  
  	function updateNote(e)
    {
      model.medical[e.target.attributes.condition.value] = e.target.value;
    }
</script>

0 likes
2 replies
robinsonryan's avatar

I've almost figured it out. I have code that works, but I get a warning in the console. I figure out how to set the keys on the ref from numeric to values that I determine:

<input type="text"
            :id="key + 'Notes'"
            :name="key + 'Notes'"
            :condition="key"
            :ref="el => { conditionNotes[key] = el }"
            :disabled="!model.medicalCondition[key]"
            @input="updateNote"
            >

And this line will allow access to the value I'm after

// This works, but it sure doesn't seem like the right way to do it.
// And I get a warning in the console:
// toRefs() expects a reactive object but received a plain one.
  toRefs(conditionNotes.value[condition]).value.value = null;

It gets the result I'm after, but the code doesn't feel very clean. I feel like there may be a better approach, but I don't know what it would be. Also, it generates a warning in the console: toRefs() expects a reactive object but received a plain one.

Here is a working SFC Playground code snippet.

Is this the correct approach to what I'm going?

1 like
robinsonryan's avatar
robinsonryan
OP
Best Answer
Level 3

Seriously. This is why you don't code at 1AM. I'm not sure what was going on when I spend two hours trying to figure this out last night, but once I figured out how to set the keys to values of my choosing, I had the solution. So this was the correct way to attach the inputs to the ref inside the v-for with known keys.

<input type="text"
	 :id="key + 'Notes'"
	 :name="key + 'Notes'"
	:condition="key"
	:ref="el => { conditionNotes[key] = el }"
	:disabled="!model.medicalCondition[key]"
	@input="updateNote"
>

And this is how to access them in the <script>

// This works!
console.log(conditionNotes.value[condition].value); //outputs value
conditionNotes.value[condition].value = null; //sets value

I figured I put the solution here for anyone else needing to know how to add items to refs inside a v-for in vue3 and then access them.

Here is the complete working component:

<template>
    <div>
        <h2>Medical Condition</h2>
        <p>Is checked: {{ model.checked }}</p>
        <p>{{ model.medical }}</p>
        <div v-for="(value, key) in model.medicalCondition" :key="key">
          <input type="checkbox" 
          	:id="key" 
          	:name="key" 
          	:value="key" 
          	@change="updateConditions">
          
          <input type="text"
          	:id="key + 'Notes'"
          	:name="key + 'Notes'"
          	:condition="key"
          	:ref="el => { conditionNotes[key] = el }"
          	:disabled="!model.medicalCondition[key]"
          	@input="updateNote"
          >
      		Condition: {{key}} Checked: {{value}}
      	</div>
    </div>
</template>
<script setup>
    import { reactive, ref, toRefs } from 'vue';
    
    const conditionNotes = ref([]);
		    
    const model = reactive(
    {
        medical: {},
        checked: false,
      	medicalCondition: {
          'arthritis': false,
          'asthma': false,
          'high blood pressure' : false
        }
    });

    function updateConditions(e)
    {
        let condition = e.target.value;
        if(e.target.checked)
        {
           model.medicalCondition[e.target.value] = true;
           model.medical[condition] = {};
        } else {
          model.medicalCondition[e.target.value] = false;
          delete model.medical[condition];
          
          // This works!
          //console.log(conditionNotes.value[condition].value); //outputs value
          conditionNotes.value[condition].value = null; //sets value	
        }
    }
  
  	function updateNote(e)
    {
      model.medical[e.target.attributes.condition.value] = e.target.value;
    }
</script>

Please or to participate in this conversation.