OLD | NEW |
| (Empty) |
1 | |
2 | |
3 Polymer({ | |
4 | |
5 is: 'iron-autogrow-textarea', | |
6 | |
7 behaviors: [ | |
8 Polymer.IronValidatableBehavior | |
9 ], | |
10 | |
11 properties: { | |
12 | |
13 /** | |
14 * Use this property instead of `value` for two-way data binding. | |
15 */ | |
16 bindValue: { | |
17 observer: '_bindValueChanged', | |
18 type: String | |
19 }, | |
20 | |
21 /** | |
22 * The initial number of rows. | |
23 * | |
24 * @attribute rows | |
25 * @type number | |
26 * @default 1 | |
27 */ | |
28 rows: { | |
29 type: Number, | |
30 value: 1, | |
31 observer: '_updateCached' | |
32 }, | |
33 | |
34 /** | |
35 * The maximum number of rows this element can grow to until it | |
36 * scrolls. 0 means no maximum. | |
37 * | |
38 * @attribute maxRows | |
39 * @type number | |
40 * @default 0 | |
41 */ | |
42 maxRows: { | |
43 type: Number, | |
44 value: 0, | |
45 observer: '_updateCached' | |
46 }, | |
47 | |
48 /** | |
49 * Set to true to mark the textarea as required. | |
50 */ | |
51 required: { | |
52 type: Boolean | |
53 }, | |
54 | |
55 /** | |
56 * The maximum length of the input value. | |
57 */ | |
58 maxlength: { | |
59 type: Number | |
60 } | |
61 | |
62 }, | |
63 | |
64 listeners: { | |
65 'input': '_onInput' | |
66 }, | |
67 | |
68 /** | |
69 * Returns the underlying textarea. | |
70 */ | |
71 get textarea() { | |
72 return this.$.textarea; | |
73 }, | |
74 | |
75 _update: function() { | |
76 this.$.mirror.innerHTML = this._valueForMirror(); | |
77 | |
78 var textarea = this.textarea; | |
79 // If the value of the textarea was updated imperatively, then we | |
80 // need to manually update bindValue as well. | |
81 if (textarea && this.bindValue != textarea.value) { | |
82 this.bindValue = textarea.value; | |
83 } | |
84 }, | |
85 | |
86 _bindValueChanged: function() { | |
87 var textarea = this.textarea; | |
88 if (!textarea) { | |
89 return; | |
90 } | |
91 | |
92 textarea.value = this.bindValue; | |
93 this._update(); | |
94 // manually notify because we don't want to notify until after setting val
ue | |
95 this.fire('bind-value-changed', {value: this.bindValue}); | |
96 }, | |
97 | |
98 _onInput: function(event) { | |
99 this.bindValue = event.path ? event.path[0].value : event.target.value; | |
100 this._update(); | |
101 }, | |
102 | |
103 _constrain: function(tokens) { | |
104 var _tokens; | |
105 tokens = tokens || ['']; | |
106 // Enforce the min and max heights for a multiline input to avoid measurem
ent | |
107 if (this.maxRows > 0 && tokens.length > this.maxRows) { | |
108 _tokens = tokens.slice(0, this.maxRows); | |
109 } else { | |
110 _tokens = tokens.slice(0); | |
111 } | |
112 while (this.rows > 0 && _tokens.length < this.rows) { | |
113 _tokens.push(''); | |
114 } | |
115 return _tokens.join('<br>') + ' '; | |
116 }, | |
117 | |
118 _valueForMirror: function() { | |
119 var input = this.textarea; | |
120 if (!input) { | |
121 return; | |
122 } | |
123 this.tokens = (input && input.value) ? input.value.replace(/&/gm, '&')
.replace(/"/gm, '"').replace(/'/gm, ''').replace(/</gm, '<').replace
(/>/gm, '>').split('\n') : ['']; | |
124 return this._constrain(this.tokens); | |
125 }, | |
126 | |
127 _updateCached: function() { | |
128 this.$.mirror.innerHTML = this._constrain(this.tokens); | |
129 } | |
130 }) | |
OLD | NEW |