2016-12-27 4 views
1

Я пытаюсь установить флажок внутри кнопки, и оба щелчка на флажке или кнопка должны переключать флажок и логическое значение, привязанное к нему из модели представления.Aurelia checkbox внутри кнопки

app.html:

<template> 
    <h1>${heading}</h1> 
    <button type="button" click.trigger="toggleIsChecked()"> 
    <input type="checkbox" checked.bind="isChecked"> ${isChecked} 
    </button> 
</template> 

app.ts:

export class App { 
    isChecked: boolean; 

    toggleIsChecked() { 
     this.isChecked = !this.isChecked; 
    } 
} 

Что происходит, что при нажатии на кнопку (вне флажком) все работает, как ожидалось. Но когда я нажимаю флажок, логическое значение в модели просмотра изменяется, но флажок не установлен или не установлен. Что может быть причиной этого?

Я пробовал разные подходы, но все они дают похожие результаты. Во время отладки я заметил, что флажок проверяется, но что-то в рамках Aurelia удаляет его почти мгновенно. Похоже, обработка событий не работает должным образом?

EDIT: Я сделал суть, так что вы можете попробовать это сами: https://gist.run/?id=4a7b2c11db33bdb37213eb4ea1b5b2b0

+0

IIRC, на флажке вы должны использовать одностороннюю привязку: 'checked.bind =" isChecked "' должно быть 'checked.one-way =" isChecked "'; Кроме того, вы, вероятно, захотите использовать click.delegate, а не триггер. –

+0

Кроме того, взгляните на этот вопрос SO: http://stackoverflow.com/questions/35296915 –

+0

Привет, спасибо за советы, но переход на одностороннюю привязку не исправил, и не щелкнул .delegate. Я прочитал вопрос SO, с которым вы связались раньше, и попробовал разные предложения там, но безуспешно. На самом деле принятый ответ на связанный с вами вопрос предполагает использование двусторонней привязки вместо односторонней. – mattipet

ответ

2

То же объяснение с Фабио Луз & собирается сделать то же самое, но вместо проверки событий имя целевого тега, Вы можете использовать поведение привязки self, как это

<template> 
    <require from='./self'></require> 
    <h1>${heading}</h1> 
    <button type="button" click.delegate="toggleIsChecked() & self"> 
    <input type="checkbox" checked.bind="isChecked"> ${isChecked} 
    </button> 
</template> 

Что self связыванию поведение делает здесь, чтобы обеспечить toggleIsChecked только пожары при нажатии на саму кнопку, а не его потомок, то же самое с этим блоком кода:

toggleIsChecked(event) { 
    if (event.target === this.button) { 
    // Do your thing 
    } 
} 

Примечание:self только что слились, но еще не выпущен. Я включил код в этом суть: https://gist.run/?id=5e66dfd996d852344a524010ae82a936

Вы можете прочитать больше о PR здесь: https://github.com/aurelia/templating-resources/pull/263

+0

Спасибо за подсказку. Раньше я не слышал о том, как себя вести. Звучит полезно. Хотя это не то, что вызывает мою проблему, и на самом деле я хочу, чтобы событие распространялось на предков этого флажка, чтобы вызывать кнопку прослушивания нажатием кнопки. – mattipet

+0

И после правильного чтения вашего ответа я заметил, что он работает так же хорошо, как и возвращение. Таким образом, есть два способа заставить это работать. Я буду отмечать это как правильный ответ, но я бы хотел, чтобы все заметили, что также возвращает true из обработчика событий. – mattipet

+0

Сначала я слышал о «я», интересный, но работает только в том случае, если флажок является единственным/прямым дочерним элементом. Я придумал следующее, которое работает для большего числа случаев (включая строки таблицы). 'click.delegate =" ($ event.target.type! == 'checkbox')? checkbox.checked =! checkbox.checked: true "' (флажок - это ссылка в поле ввода: ref = "checkbox") – Matt

3

Это не основа Aurelia, что «удаление» проверку. Что происходит в том, что при нажатии на флажок, то isChecked автоматически устанавливается на true, затем toggleIsChecked() обжигают и isChecked установлен в false (isChecked установлен дважды при нажатии флажок). Чтобы решить эту проблему, вы не должны устанавливать isChecked, если цель checkbox. Что-то вроде этого:

JS

toggleIsChecked(event) { 
    if (event.target.tagName === 'INPUT') { 
    return true; //checkbox has been clicked, do nothing! 
    } 
    this.isChecked = !this.isChecked; 
} 

HTML

<button type="button" click.trigger="toggleIsChecked($event)"> 
    <input type="checkbox" checked.bind="isChecked"> ${isChecked} 
</button> 
+0

Это не то, что происходит. Если бы это было тогда, то значение в модели представления также не изменилось бы (или изменилось бы дважды на самом деле). Здесь происходит то, что обработчик события по умолчанию никогда не вызывается, и поэтому флажок никогда не проверяется/не проверяется. Я опубликую рабочий пояс и объясню, как это должно быть сделано. – mattipet

1

Добрые люди в чате Aurelia GITTER предоставил мне ответ. То, что происходит в моем сущности, заключается в том, что обработчик события по умолчанию не вызывается. Причина этого заключается в том, что Aurelia автоматически вызывает функцию event.preventDefault(). Чтобы вызвать обработчик события по умолчанию, я должен вернуть true из моего собственного обработчика событий.Вот рабочий принцип, доказывающий, как он работает: https://gist.run/?id=3cb545572065cffd737f98788a4105a1

Благодарим всех вас за ответы. Я решил ответить на это сам, так как получил ответ от чата Gitter, но это престиж относится к удивительному сообществу Aurelia и особенно к @CasiOo.