@@ -16,37 +16,74 @@ import * as marked from 'marked'
16
16
export default function onHasCompletion ( cm , data , onHintInformationRender ) {
17
17
const CodeMirror = require ( 'codemirror' )
18
18
19
+ let wrapper
19
20
let information
20
21
let deprecation
21
22
22
- // When a hint result is selected, we augment the UI with information .
23
+ // When a hint result is selected, we touch the UI.
23
24
CodeMirror . on ( data , 'select' , ( ctx , el ) => {
24
25
// Only the first time (usually when the hint UI is first displayed)
25
- // do we create the information nodes.
26
- if ( ! information ) {
26
+ // do we create the wrapping node.
27
+ if ( ! wrapper ) {
28
+ // Wrap the existing hint UI, so we have a place to put information.
27
29
const hintsUl = el . parentNode
30
+ const container = hintsUl . parentNode
31
+ wrapper = document . createElement ( 'div' )
32
+ container . appendChild ( wrapper )
33
+
34
+ // CodeMirror vertically inverts the hint UI if there is not enough
35
+ // space below the cursor. Since this modified UI appends to the bottom
36
+ // of CodeMirror's existing UI, it could cover the cursor. This adjusts
37
+ // the positioning of the hint UI to accomodate.
38
+ let top = hintsUl . style . top
39
+ let bottom = ''
40
+ const cursorTop = cm . cursorCoords ( ) . top
41
+ if ( parseInt ( top , 10 ) < cursorTop ) {
42
+ top = ''
43
+ bottom = window . innerHeight - cursorTop + 3 + 'px'
44
+ }
45
+
46
+ // Style the wrapper, remove positioning from hints. Note that usage
47
+ // of this option will need to specify CSS to remove some styles from
48
+ // the existing hint UI.
49
+ wrapper . className = 'CodeMirror-hints-wrapper'
50
+ wrapper . style . left = hintsUl . style . left
51
+ wrapper . style . top = top
52
+ wrapper . style . bottom = bottom
53
+ hintsUl . style . left = ''
54
+ hintsUl . style . top = ''
28
55
29
56
// This "information" node will contain the additional info about the
30
57
// highlighted typeahead option.
31
58
information = document . createElement ( 'div' )
32
59
information . className = 'CodeMirror-hint-information'
33
- hintsUl . appendChild ( information )
34
60
35
61
// This "deprecation" node will contain info about deprecated usage.
36
62
deprecation = document . createElement ( 'div' )
37
63
deprecation . className = 'CodeMirror-hint-deprecation'
38
- hintsUl . appendChild ( deprecation )
64
+
65
+ if ( bottom ) {
66
+ wrapper . appendChild ( deprecation )
67
+ wrapper . appendChild ( information )
68
+ wrapper . appendChild ( hintsUl )
69
+ } else {
70
+ wrapper . appendChild ( hintsUl )
71
+ wrapper . appendChild ( information )
72
+ wrapper . appendChild ( deprecation )
73
+ }
39
74
40
75
// When CodeMirror attempts to remove the hint UI, we detect that it was
41
- // removed and in turn remove the information nodes.
76
+ // removed from our wrapper and in turn remove the wrapper from the
77
+ // original container.
42
78
let onRemoveFn
43
- hintsUl . addEventListener (
79
+ wrapper . addEventListener (
44
80
'DOMNodeRemoved' ,
45
81
( onRemoveFn = event => {
46
82
if ( event . target === hintsUl ) {
47
- hintsUl . removeEventListener ( 'DOMNodeRemoved' , onRemoveFn )
83
+ wrapper . removeEventListener ( 'DOMNodeRemoved' , onRemoveFn )
84
+ wrapper . parentNode . removeChild ( wrapper )
85
+ wrapper = null
48
86
information = null
49
- deprecation = null
50
87
onRemoveFn = null
51
88
}
52
89
} ) ,
0 commit comments