Skip to content

Commit 31e5c37

Browse files
author
jackyjjc
committed
Added element selector
1 parent 092f33e commit 31e5c37

File tree

8 files changed

+220
-9
lines changed

8 files changed

+220
-9
lines changed

wat-code-editor/wat-code-editor.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ Polymer('wat-code-editor', {
3838
} else {
3939
this.selected = window.localStorage['wat-selected-editors'].split(',');
4040
}
41+
this.previewFrame = this.$['preview-frame'];
4142
this.updatePreview();
4243
},
4344

wat-target-selector/index.html

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
<!--
2+
Copyright 2014 Google Inc. All Rights Reserved.
3+
4+
Licensed under the Apache License, Version 2.0 (the "License");
5+
you may not use this file except in compliance with the License.
6+
You may obtain a copy of the License at
7+
8+
http://www.apache.org/licenses/LICENSE-2.0
9+
10+
Unless required by applicable law or agreed to in writing, software
11+
distributed under the License is distributed on an "AS IS" BASIS,
12+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
See the License for the specific language governing permissions and
14+
15+
limitations under the License.
16+
-->
17+
18+
<!DOCTYPE html>
19+
20+
<script src="../../web-animations-js/web-animations.js"></script>
21+
<script src="../../platform/platform.js"></script>
22+
<link rel="import" href="wat-target-selector.html">
23+
<link rel="import" href="../internal/wat-button/wat-button.html">
24+
25+
<iframe id="frame"></iframe>
26+
<wat-target-selector id="selector"></wat-target-selector>
27+
<script>
28+
var frame = document.querySelector('#frame');
29+
var d = frame.contentDocument;
30+
d.open();
31+
d.write('<style>'+
32+
'div {' +
33+
'width: 32px;' +
34+
'height: 32px;' +
35+
'border: 1px solid black;' +
36+
'}\n' +
37+
'.selected {' +
38+
'border: 1px solid red;'+
39+
'}</style>' _+
40+
'<div id="div1"></div>' +
41+
'<div id="div2"></div>' +
42+
'<div id="div3"></div>');
43+
d.close();
44+
45+
document.addEventListener('select-target', function(e) {
46+
var divs = frame.contentDocument.getElementsByTagName('*');
47+
for (var i = 0; i < divs.length; i++) {
48+
divs[i].classList.remove('selected');
49+
}
50+
var selectedDiv = frame.contentDocument.getElementById(e.detail);
51+
selectedDiv.classList.add('selected');
52+
});
53+
54+
document.addEventListener('polymer-ready', function() {
55+
var selector = document.querySelector('#selector');
56+
selector.frame = frame;
57+
selector.update();
58+
});
59+
</script>
Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
<!--
2+
Copyright 2014 Google Inc. All Rights Reserved.
3+
4+
Licensed under the Apache License, Version 2.0 (the "License");
5+
you may not use this file except in compliance with the License.
6+
You may obtain a copy of the License at
7+
8+
http://www.apache.org/licenses/LICENSE-2.0
9+
10+
Unless required by applicable law or agreed to in writing, software
11+
distributed under the License is distributed on an "AS IS" BASIS,
12+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
See the License for the specific language governing permissions and
14+
15+
limitations under the License.
16+
-->
17+
<link rel="import" href="../../polymer/polymer.html">
18+
19+
<polymer-element name="wat-target-selector" attributes="frame selected">
20+
<template>
21+
<style>
22+
:host {
23+
display: block;
24+
width: 330px;
25+
}
26+
input {
27+
margin-bottom: 15px;
28+
}
29+
</style>
30+
<div id="radio-button-group">
31+
<template repeat="{{e in elements}}">
32+
<input type="radio" name="id" value="{{e.id}}" checked="{{e.id === selected ? true : false}}">{{e.id}}<br>
33+
</template>
34+
</div>
35+
<wat-button title="select" on-click="{{selectElement}}">Select</wat-button>
36+
</template>
37+
<script>
38+
Polymer('wat-target-selector', {
39+
frame: null,
40+
selected: null,
41+
update: function() {
42+
if (!this.frame) {
43+
return;
44+
}
45+
var elems = this.frame.contentDocument.body.getElementsByTagName('*');
46+
var elemsWithID = [];
47+
for (var i = 0; i < elems.length; i++) {
48+
if (elems[i].id) {
49+
elemsWithID.push(elems[i]);
50+
}
51+
}
52+
53+
this.elements = elemsWithID;
54+
},
55+
selectElement: function() {
56+
var selected = this.$['radio-button-group'].querySelector('input[name = "id"]:checked');
57+
if (!selected) {
58+
return;
59+
}
60+
this.selected = selected.value;
61+
},
62+
});
63+
</script>
64+
</polymer-element>

wat-timeditem-inspector/wat-timeditem-inspector.css

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -26,15 +26,14 @@
2626
vertical-align: middle;
2727
}
2828

29-
#launch-button {
29+
.launch-button {
3030
display: inline-flex;
3131
margin-left: 0.2em;
3232
width: calc(35px - 0.5em);
3333
height: 20px;
3434
}
3535

36-
#launch-button ^^ button {
37-
36+
.launch-button ^^ button {
3837
line-height: 6px;
3938
padding: 0 0 2px 0;
4039
}
@@ -66,6 +65,10 @@
6665
padding: 1px 2px;
6766
}
6867

68+
.property #animTarget {
69+
width: calc(65% - 40px);
70+
}
71+
6972
.property .field:focus {
7073
border: 1px solid rgba(66,133,244,1);
7174
outline: none;

wat-timeditem-inspector/wat-timeditem-inspector.html

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,14 +21,22 @@
2121
<link rel="import" href="../internal/wat-button/wat-button.html">
2222
<link rel="import" href="../wat-bezier/wat-bezier.html">
2323
<link rel="import" href="../wat-step/wat-step.html">
24+
<link rel="import" href="../wat-target-selector/wat-target-selector.html">
2425
<link href="//netdna.bootstrapcdn.com/font-awesome/4.0.3/css/font-awesome.css" rel="stylesheet">
2526

26-
<polymer-element name="wat-timeditem-inspector" attributes="timedItem">
27+
<polymer-element name="wat-timeditem-inspector" attributes="timedItem previewFrame">
2728
<template>
2829
<link href="//netdna.bootstrapcdn.com/font-awesome/4.0.3/css/font-awesome.css" rel="stylesheet">
2930
<link rel="stylesheet" type="text/css" href="wat-timeditem-inspector.css">
3031

3132
<div id="property-container">
33+
<div class="property {{timedItem.type ? 'hidden' : ''}}">
34+
<label for="animTarget">target:</label>
35+
<input class="field" id="animTarget" placeholder="DOM Element ID"
36+
value="{{$.targetSelector.selected}}" on-change="{{animationTargetChanged}}">
37+
<wat-button class="launch-button" title="Launch Element Selector"
38+
on-click="{{showElementSelectorContainer}}"></wat-button>
39+
</div>
3240
<div class="property">
3341
<label for="delay">delay:</label>
3442
<input class="field" id="delay" type="number"
@@ -61,7 +69,7 @@
6169
</template>
6270
<option value="custom">custom</option>
6371
</select>
64-
<wat-button id="launch-button" title="Launch Easing Editor"
72+
<wat-button class="launch-button" title="Launch Easing Editor"
6573
on-click="{{showEasingEditorContainer}}"></wat-button>
6674
</div>
6775
<div class="{{easing == 'custom' ? 'property' : 'hidden'}}">
@@ -104,6 +112,16 @@
104112
<wat-bezier id="wat-bezier" class="hidden"></wat-bezier>
105113
<wat-step id="wat-step" class="hidden"></wat-step>
106114
</div>
115+
<div id="target-selector-container" class="hidden">
116+
<div>
117+
<wat-button id="back-button" on-click="{{showPropertyContainer}}"
118+
title="Back">
119+
<i class="fa fa-reply"></i>
120+
</wat-button>
121+
</div>
122+
<wat-target-selector id="targetSelector" frame="{{previewFrame}}">
123+
</wat-target-selector>
124+
</div>
107125
</template>
108126

109127
<script src="wat-timeditem-inspector.js"></script>

wat-timeditem-inspector/wat-timeditem-inspector.js

Lines changed: 33 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ Polymer('wat-timeditem-inspector', {
2525

2626
observe: {
2727
'timedItem.specified.easing': 'timedItemEasingChanged',
28+
'$.targetSelector.selected': 'animationTargetChanged',
2829
},
2930

3031
created: function() {
@@ -52,12 +53,13 @@ Polymer('wat-timeditem-inspector', {
5253
this.easing = this.timedItem.specified.easing;
5354
this.$['wat-bezier'].timedItem = this.timedItem;
5455
this.$['wat-step'].timedItem = this.timedItem;
56+
this.$.targetSelector.selected = this.timedItem.target ?
57+
this.timedItem.target.id : '';
5558
} else {
5659
this.timedItem = new Animation(null, null, 0);
5760
}
5861
},
5962

60-
6163
timedItemEasingChanged: function() {
6264
if (!this.timedItem) {
6365
return;
@@ -71,6 +73,29 @@ Polymer('wat-timeditem-inspector', {
7173
}
7274
this.showAppropriateEasingEditor();
7375
},
76+
77+
previewFrameChanged: function() {
78+
var elementSelector = this.$.targetSelector;
79+
this.previewFrame.addEventListener('load',
80+
elementSelector.update.bind(elementSelector));
81+
},
82+
83+
animationTargetChanged: function() {
84+
var doc = this.previewFrame.contentDocument;
85+
var elem = doc.getElementById(this.$.targetSelector.selected);
86+
if (!elem) {
87+
return;
88+
}
89+
var oldAnim = this.timedItem;
90+
var newAnim = new Animation(elem, oldAnim.effect, oldAnim.specified);
91+
newAnim.name = oldAnim.name;
92+
if (oldAnim.parent) {
93+
oldAnim.before(newAnim);
94+
oldAnim.remove();
95+
}
96+
this.timedItem = newAnim;
97+
this.showPropertyContainer();
98+
},
7499

75100
showAppropriateEasingEditor: function() {
76101
if (this.bezierEasings.indexOf(this.timedItem.specified.easing) >= 0 ||
@@ -90,11 +115,18 @@ Polymer('wat-timeditem-inspector', {
90115
this.$['easing-editor-container'].className = '';
91116
},
92117

118+
showElementSelectorContainer: function() {
119+
this.$['property-container'].className = 'hidden';
120+
this.$['target-selector-container'].className = '';
121+
this.$.targetSelector.update();
122+
},
123+
93124
showPropertyContainer: function() {
94125
if (this.presetEasings.indexOf(this.timedItem.specified.easing) >= 0) {
95126
this.easing = this.timedItem.specified.easing;
96127
}
97128
this.$['easing-editor-container'].className = 'hidden';
129+
this.$['target-selector-container'].className = 'hidden';
98130
this.$['property-container'].className = '';
99131
}
100132
});

wat-wat/wat-wat.html

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -117,8 +117,7 @@
117117
</wat-menu>
118118

119119
<wat-dock id="dockRight" side="right">
120-
<wat-timeditem-inspector class="paper" timedItem="{{selected || selectedRoot}}">
121-
</wat-timeditem-inspector>
120+
<wat-timeditem-inspector id="inspector" class="paper"></wat-timeditem-inspector>
122121
</wat-dock>
123122
</div>
124123

wat-wat/wat-wat.js

Lines changed: 36 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -63,13 +63,16 @@ Polymer('wat-wat', {
6363
this.$.github.toast(event.detail);
6464
}.bind(this));
6565

66+
this.$.inspector.previewFrame = this.$['wat-code-editor'].previewFrame;
67+
6668
this.loadAnimation();
6769
},
6870

6971
observe: {
7072
'$.dockRight.collapsed': 'dockRightCollapsedChanged',
7173
'$.dockBottom.collapsed': 'dockBottomCollapsedChanged',
72-
'$.dockBottom.shadowRoot.childNodes.length' : 'updateTimeline'
74+
'$.dockBottom.shadowRoot.childNodes.length' : 'updateTimeline',
75+
'$.inspector.timedItem': 'inspectorItemChanged',
7376
},
7477

7578
updateTimeline: function() {
@@ -104,6 +107,38 @@ Polymer('wat-wat', {
104107
window.localStorage['wat-show-print-margin'] = this.showPrintMargin;
105108
},
106109

110+
// The follow three functions are replacements for the timedItem binding
111+
// between wat-wat and wat-timedItem-inspector. We can't use a simple
112+
// binding because the inspector may create a new Animation when changing
113+
// the target of an animation. In that case we need to change both the
114+
// selectedRoot and the current player's source item.
115+
selectedChanged: function() {
116+
if (this.selected !== null) {
117+
this.$.inspector.timedItem = this.selected;
118+
} else {
119+
this.$.inspector.timedItem = this.selectedRoot;
120+
}
121+
},
122+
123+
selectedRootChanged: function() {
124+
if (this.selected === null) {
125+
this.$.inspector.timedItem = this.selectedRoot;
126+
}
127+
},
128+
129+
inspectorItemChanged: function() {
130+
// Inspector changed the selected item, if the selected item is root,
131+
// change the root. Otherwise just change the selcted item.
132+
if (this.selected === this.selectedRoot) {
133+
var newAnim = this.$.inspector.timedItem;
134+
if (this.selectedRoot && this.selectedRoot.player) {
135+
this.selectedRoot.player.source = newAnim;
136+
}
137+
this.selectedRoot = newAnim;
138+
}
139+
this.selected = this.$.inspector.timedItem;
140+
},
141+
107142
getStorageValue: function(localStorageKey, defaultValue) {
108143
return window.localStorage[localStorageKey] === undefined ? defaultValue :
109144
JSON.parse(window.localStorage[localStorageKey]);

0 commit comments

Comments
 (0)