Skip to content

Commit 72c19ec

Browse files
committed
Fix 7304: show correct quickinfo on "this" in type position (#8508)
* Show correct quickinfo when using this in type position * Split quickinfo test into smaller files and add test case
1 parent 955cc69 commit 72c19ec

File tree

6 files changed

+73
-62
lines changed

6 files changed

+73
-62
lines changed

src/compiler/checker.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5211,6 +5211,7 @@ namespace ts {
52115211
case SyntaxKind.NullKeyword:
52125212
return nullType;
52135213
case SyntaxKind.ThisType:
5214+
case SyntaxKind.ThisKeyword:
52145215
return getTypeFromThisTypeNode(node);
52155216
case SyntaxKind.StringLiteralType:
52165217
return getTypeFromStringLiteralTypeNode(<StringLiteralTypeNode>node);
@@ -12509,7 +12510,7 @@ namespace ts {
1250912510

1251012511
// Checks an expression and returns its type. The contextualMapper parameter serves two purposes: When
1251112512
// contextualMapper is not undefined and not equal to the identityMapper function object it indicates that the
12512-
// expression is being inferentially typed (section 4.12.2 in spec) and provides the type mapper to use in
12513+
// expression is being inferentially typed (section 4.15.2 in spec) and provides the type mapper to use in
1251312514
// conjunction with the generic contextual type. When contextualMapper is equal to the identityMapper function
1251412515
// object, it serves as an indicator that all contained function and arrow expressions should be considered to
1251512516
// have the wildcard function type; this form of type check is used during overload resolution to exclude

src/compiler/utilities.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1056,6 +1056,7 @@ namespace ts {
10561056

10571057
export function isExpression(node: Node): boolean {
10581058
switch (node.kind) {
1059+
case SyntaxKind.ThisKeyword:
10591060
case SyntaxKind.SuperKeyword:
10601061
case SyntaxKind.NullKeyword:
10611062
case SyntaxKind.TrueKeyword:

tests/cases/fourslash/quickInfoOnThis.ts

Lines changed: 4 additions & 61 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
////function wrapper(wrapped: { (): void; }) { }
66
////class Foo {
77
//// n: number;
8+
//// prop1: th/*0*/is;
89
//// public explicitThis(this: this) {
910
//// wrapper(
1011
//// function explicitVoid(this: void) {
@@ -20,43 +21,9 @@
2021
//// console.log(th/*6*/is);
2122
//// }
2223
////}
23-
////class Bar<T> {
24-
//// public explicitThis(this: this) {
25-
//// console.log(th/*7*/is);
26-
//// }
27-
//// public explicitClass(this: Bar<T>) {
28-
//// console.log(thi/*8*/s);
29-
//// }
30-
////}
31-
////
32-
////function implicitAny(x: number): void {
33-
//// return th/*9*/is;
34-
////}
35-
////function explicitVoid(th/*10*/is: void, x: number): void {
36-
//// return th/*11*/is;
37-
////}
38-
////function explicitInterface(th/*12*/is: Restricted): void {
39-
//// console.log(thi/*13*/s);
40-
////}
41-
////function explicitLiteral(th/*14*/is: { n: number }): void {
42-
//// console.log(th/*15*/is);
43-
////}
44-
////
45-
////interface ContextualInterface {
46-
//// m: number;
47-
//// method(this: this, n: number);
48-
////}
49-
////let o: ContextualInterface = {
50-
//// m: 12,
51-
//// method(n) {
52-
//// let x = this/*16*/.m;
53-
//// }
54-
////}
55-
////interface ContextualInterface2 {
56-
//// (this: void, n: number): void;
57-
////}
58-
////let contextualInterface2: ContextualInterface2 = function (th/*17*/is, n) { }
5924

25+
goTo.marker('0');
26+
verify.quickInfoIs('this: this');
6027
goTo.marker('1');
6128
verify.quickInfoIs('void');
6229
goTo.marker('2');
@@ -68,28 +35,4 @@ verify.quickInfoIs('this: Restricted');
6835
goTo.marker('5');
6936
verify.quickInfoIs('(parameter) this: Foo');
7037
goTo.marker('6');
71-
verify.quickInfoIs('this: Foo');
72-
goTo.marker('7');
73-
verify.quickInfoIs('this: this');
74-
goTo.marker('8');
75-
verify.quickInfoIs('this: Bar<T>');
76-
goTo.marker('9');
77-
verify.quickInfoIs('any');
78-
goTo.marker('10');
79-
verify.quickInfoIs('(parameter) this: void');
80-
goTo.marker('11');
81-
verify.quickInfoIs('void');
82-
goTo.marker('12');
83-
verify.quickInfoIs('(parameter) this: Restricted');
84-
goTo.marker('13');
85-
verify.quickInfoIs('this: Restricted');
86-
goTo.marker('14');
87-
88-
verify.quickInfoIs('(parameter) this: {\n n: number;\n}');
89-
goTo.marker('15');
90-
verify.quickInfoIs('this: {\n n: number;\n}');
91-
92-
goTo.marker('16');
93-
verify.quickInfoIs('this: ContextualInterface');
94-
goTo.marker('17');
95-
verify.quickInfoIs('(parameter) this: void');
38+
verify.quickInfoIs('this: Foo');
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
/// <reference path='fourslash.ts' />
2+
////class Bar<T> {
3+
//// public explicitThis(this: this) {
4+
//// console.log(th/*1*/is);
5+
//// }
6+
//// public explicitClass(this: Bar<T>) {
7+
//// console.log(thi/*2*/s);
8+
//// }
9+
////}
10+
11+
goTo.marker('1');
12+
verify.quickInfoIs('this: this');
13+
goTo.marker('2');
14+
verify.quickInfoIs('this: Bar<T>');
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
/// <reference path='fourslash.ts' />
2+
////interface Restricted {
3+
//// n: number;
4+
////}
5+
////function implicitAny(x: number): void {
6+
//// return th/*1*/is;
7+
////}
8+
////function explicitVoid(th/*2*/is: void, x: number): void {
9+
//// return th/*3*/is;
10+
////}
11+
////function explicitInterface(th/*4*/is: Restricted): void {
12+
//// console.log(thi/*5*/s);
13+
////}
14+
////function explicitLiteral(th/*6*/is: { n: number }): void {
15+
//// console.log(th/*7*/is);
16+
////}
17+
18+
goTo.marker('1');
19+
verify.quickInfoIs('any');
20+
goTo.marker('2');
21+
verify.quickInfoIs('(parameter) this: void');
22+
goTo.marker('3');
23+
verify.quickInfoIs('void');
24+
goTo.marker('4');
25+
verify.quickInfoIs('(parameter) this: Restricted');
26+
goTo.marker('5');
27+
verify.quickInfoIs('this: Restricted');
28+
goTo.marker('6');
29+
30+
verify.quickInfoIs('(parameter) this: {\n n: number;\n}');
31+
goTo.marker('7');
32+
verify.quickInfoIs('this: {\n n: number;\n}');
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
/// <reference path='fourslash.ts' />
2+
////interface ContextualInterface {
3+
//// m: number;
4+
//// method(this: this, n: number);
5+
////}
6+
////let o: ContextualInterface = {
7+
//// m: 12,
8+
//// method(n) {
9+
//// let x = this/*1*/.m;
10+
//// }
11+
////}
12+
////interface ContextualInterface2 {
13+
//// (this: void, n: number): void;
14+
////}
15+
////let contextualInterface2: ContextualInterface2 = function (th/*2*/is, n) { }
16+
17+
goTo.marker('1');
18+
verify.quickInfoIs('this: ContextualInterface');
19+
goTo.marker('2');
20+
verify.quickInfoIs('(parameter) this: void');

0 commit comments

Comments
 (0)