Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(161)

Side by Side Diff: site/try/src/editor.dart

Issue 2232273004: Delete site/try (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 4 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file.
4
5 library trydart.editor;
6
7 import 'dart:html';
8
9 import 'package:compiler/src/scanner/string_scanner.dart' show
10 StringScanner;
11
12 import 'package:compiler/src/tokens/token.dart' show
13 ErrorToken,
14 Token;
15
16 import 'package:compiler/src/tokens/token_constants.dart' show
17 EOF_TOKEN;
18
19 import 'ui.dart' show
20 currentTheme,
21 hackDiv,
22 interaction,
23 mainEditorPane,
24 observer,
25 outputDiv;
26
27 import 'decoration.dart' show
28 CodeCompletionDecoration,
29 Decoration,
30 DiagnosticDecoration,
31 error,
32 info,
33 warning;
34
35 import 'selection.dart' show
36 isCollapsed;
37
38 import 'shadow_root.dart' show
39 getShadowRoot;
40
41 import 'settings.dart' as settings;
42
43 const String INDENT = '\u{a0}\u{a0}';
44
45 Set<String> seenIdentifiers;
46
47 Element moveActive(int distance, Node ui) {
48 var /* ShadowRoot or Element */ root = getShadowRoot(ui);
49 List<Element> entries = root.querySelectorAll('.dart-static>.dart-entry');
50 int activeIndex = -1;
51 for (var i = 0; i < entries.length; i++) {
52 if (entries[i].classes.contains('activeEntry')) {
53 activeIndex = i;
54 break;
55 }
56 }
57 int newIndex = activeIndex + distance;
58 Element currentEntry;
59 if (0 <= newIndex && newIndex < entries.length) {
60 currentEntry = entries[newIndex];
61 }
62 if (currentEntry == null) return null;
63 if (0 <= newIndex && activeIndex != -1) {
64 entries[activeIndex].classes.remove('activeEntry');
65 }
66 Element staticNode = root.querySelector('.dart-static');
67 String visibility = computeVisibility(currentEntry, staticNode);
68 print(visibility);
69 var serverResults = root.querySelectorAll('.dart-server>.dart-entry');
70 var serverResultCount = serverResults.length;
71 if (serverResultCount > 0) {
72 switch (visibility) {
73 case obscured:
74 case hidden: {
75 Rectangle cr = currentEntry.getBoundingClientRect();
76 Rectangle sr = staticNode.getBoundingClientRect();
77 Element entry = serverResults[0];
78 entry.remove();
79 currentEntry.parentNode.insertBefore(entry, currentEntry);
80 currentEntry = entry;
81 serverResultCount--;
82
83 staticNode.style.maxHeight = '${sr.boundingBox(cr).height}px';
84 }
85 }
86 } else {
87 currentEntry.scrollIntoView();
88 }
89 if (serverResultCount == 0) {
90 root.querySelector('.dart-server').style.display = 'none';
91 }
92 if (currentEntry != null) {
93 currentEntry.classes.add('activeEntry');
94 }
95 // Discard mutations.
96 observer.takeRecords();
97 return currentEntry;
98 }
99
100 const visible = 'visible';
101 const obscured = 'obscured';
102 const hidden = 'hidden';
103
104 String computeVisibility(Element node, [Element parent]) {
105 Rectangle nr = node.getBoundingClientRect();
106 if (parent == null) parent = node.parentNode;
107 Rectangle pr = parent.getBoundingClientRect();
108
109 if (pr.containsRectangle(nr)) return visible;
110
111 if (pr.intersects(nr)) return obscured;
112
113 return hidden;
114 }
115
116 var activeCompletion;
117 num minSuggestionWidth = 0;
118
119 /// Returns the [Element] which encloses the current collapsed selection, if it
120 /// exists.
121 Element getElementAtSelection() {
122 Selection selection = window.getSelection();
123 if (!isCollapsed(selection)) return null;
124 var anchorNode = selection.anchorNode;
125 if (!mainEditorPane.contains(anchorNode)) return null;
126 if (mainEditorPane == anchorNode) return null;
127 int type = anchorNode.nodeType;
128 if (type != Node.TEXT_NODE) return null;
129 Text text = anchorNode;
130 var parent = text.parent;
131 if (parent is! Element) return null;
132 if (mainEditorPane == parent) return null;
133 return parent;
134 }
135
136 bool isMalformedInput = false;
137
138 addDiagnostic(String kind, String message, int begin, int end) {
139 observer.disconnect();
140 Selection selection = window.getSelection();
141 int offset = 0;
142 int anchorOffset = 0;
143 bool hasSelection = false;
144 Node anchorNode = selection.anchorNode;
145 bool foundNode = false;
146 void walk4(Node node) {
147 // TODO(ahe): Use TreeWalker when that is exposed.
148 int type = node.nodeType;
149 if (type == Node.TEXT_NODE || type == Node.CDATA_SECTION_NODE) {
150 CharacterData cdata = node;
151 // print('walking: ${node.data}');
152 if (anchorNode == node) {
153 hasSelection = true;
154 anchorOffset = selection.anchorOffset + offset;
155 }
156 int newOffset = offset + cdata.length;
157 if (offset <= begin && begin < newOffset) {
158 hasSelection = node == anchorNode;
159 anchorOffset = selection.anchorOffset;
160 var alert;
161 if (kind == 'error') {
162 alert = error(message);
163 } else if (kind == 'warning') {
164 alert = warning(message);
165 } else {
166 alert = info(message);
167 }
168 Element parent = node.parentNode;
169 if (parent.classes.contains("diagnostic") &&
170 !interaction.oldDiagnostics.contains(parent)) {
171 Element other = parent.firstChild;
172 other.remove();
173 SpanElement wrapper = new SpanElement()
174 ..classes.add('diagnostic')
175 ..style.fontWeight = 'normal';
176
177 var root = getShadowRoot(wrapper);
178 if (root is ShadowRoot) {
179 // When https://code.google.com/p/chromium/issues/detail?id=313458
180 // is fixed:
181 // var link = new LinkElement()
182 // ..rel = "stylesheet"
183 // ..type = "text/css"
184 // ..href = "dartlang-style.css";
185 // root.append(link);
186 root.append(
187 new StyleElement()..text = '@import url(dartlang-style.css)');
188 }
189 root
190 ..append(other)
191 ..append(alert);
192 other.style.display = 'block';
193 alert.style.display = 'block';
194 parent.append(wrapper);
195 } else {
196 if (interaction.oldDiagnostics.contains(parent)) {
197 node.remove();
198 parent.replaceWith(node);
199 }
200 Node marker = new Text("");
201 node.replaceWith(marker);
202 // TODO(ahe): Don't highlight everything in the node. Find the
203 // relevant token (works for now as we create a node for each token,
204 // which is probably not great for performance).
205 marker.replaceWith(diagnostic(node, alert));
206 if (hasSelection) {
207 selection.collapse(node, anchorOffset);
208 }
209 }
210 foundNode = true;
211 return;
212 }
213 offset = newOffset;
214 } else if (type == Node.ELEMENT_NODE) {
215 Element element = node;
216 CssClassSet classes = element.classes;
217 if (classes.contains('alert') ||
218 classes.contains('dart-code-completion')) {
219 return;
220 }
221 }
222
223 var child = node.firstChild;
224 while(child != null && !foundNode) {
225 walk4(child);
226 child = child.nextNode;
227 }
228 }
229 walk4(mainEditorPane);
230
231 if (!foundNode) {
232 outputDiv.appendText('$message\n');
233 }
234
235 observer.takeRecords();
236 observer.observe(
237 mainEditorPane, childList: true, characterData: true, subtree: true);
238 }
239
240 Decoration getDecoration(Token token) {
241 if (token is ErrorToken) {
242 // TODO(ahe): Remove side effects from this method. It only leads to
243 // confusion.
244 isMalformedInput = true;
245 return new DiagnosticDecoration('error', token.assertionMessage);
246 }
247 String tokenValue = token.value;
248 String tokenInfo = token.info.value;
249 if (tokenInfo == 'string') return currentTheme.string;
250 if (tokenInfo == 'identifier') {
251 seenIdentifiers.add(tokenValue);
252 Decoration decoration = currentTheme.foreground;
253 if (settings.enableCodeCompletion.value) {
254 decoration = CodeCompletionDecoration.from(decoration);
255 }
256 return decoration;
257 }
258 if (tokenInfo == 'keyword') return currentTheme.keyword;
259 if (tokenInfo == 'comment') return currentTheme.singleLineComment;
260 if (tokenInfo == 'malformed input') {
261 // TODO(ahe): Remove side effects from this method. It only leads to
262 // confusion.
263 isMalformedInput = true;
264 return new DiagnosticDecoration('error', tokenValue);
265 }
266 return currentTheme.foreground;
267 }
268
269 diagnostic(content, tip) {
270 if (content is String) {
271 content = new Text(content);
272 }
273 if (content is! List) {
274 content = [content];
275 }
276 return new AnchorElement()
277 ..classes.add('diagnostic')
278 ..append(tip) // Should be first for better Firefox editing.
279 ..nodes.addAll(content);
280 }
OLDNEW
« dart.gyp ('K') | « site/try/src/decoration.dart ('k') | site/try/src/extract_theme.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698