@@ -19,13 +19,16 @@ AndroidStudio get androidStudio => context.get<AndroidStudio>();
1919
2020// Linux/Windows:
2121// $HOME/.AndroidStudioX.Y/system/.home
22+ // $HOME/.cache/Google/AndroidStudioX.Y/.home
2223
2324// macOS:
2425// /Applications/Android Studio.app/Contents/
2526// $HOME/Applications/Android Studio.app/Contents/
2627
28+ // Match Android Studio >= 4.1 base folder (AndroidStudio*.*)
29+ // and < 4.1 (.AndroidStudio*.*)
2730final RegExp _dotHomeStudioVersionMatcher =
28- RegExp (r'^\.(AndroidStudio[^\d]*)([\d.]+)' );
31+ RegExp (r'^\.? (AndroidStudio[^\d]*)([\d.]+)' );
2932
3033String get javaPath => androidStudio? .javaPath;
3134
@@ -104,14 +107,30 @@ class AndroidStudio implements Comparable<AndroidStudio> {
104107 if (studioAppName == null || version == null ) {
105108 return null ;
106109 }
110+
111+ final int major = version? .major;
112+ final int minor = version? .minor;
113+
114+ // The install path is written in a .home text file,
115+ // it location is in <base dir>/.home for Android Studio >= 4.1
116+ // and <base dir>/system/.home for Android Studio < 4.1
117+ String dotHomeFilePath;
118+
119+ if (major != null && major >= 4 && minor != null && minor >= 1 ) {
120+ dotHomeFilePath = globals.fs.path.join (homeDotDir.path, '.home' );
121+ } else {
122+ dotHomeFilePath =
123+ globals.fs.path.join (homeDotDir.path, 'system' , '.home' );
124+ }
125+
107126 String installPath;
127+
108128 try {
109- installPath = globals.fs
110- .file (globals.fs.path.join (homeDotDir.path, 'system' , '.home' ))
111- .readAsStringSync ();
129+ installPath = globals.fs.file (dotHomeFilePath).readAsStringSync ();
112130 } on Exception {
113131 // ignored, installPath will be null, which is handled below
114132 }
133+
115134 if (installPath != null && globals.fs.isDirectorySync (installPath)) {
116135 return AndroidStudio (
117136 installPath,
@@ -161,6 +180,24 @@ class AndroidStudio implements Comparable<AndroidStudio> {
161180 );
162181 }
163182 } else {
183+ // JetBrains Toolbox write plugins here
184+ final String toolboxPluginsPath = '$directory .plugins' ;
185+
186+ if (globals.fs.directory (toolboxPluginsPath).existsSync ()) {
187+ return toolboxPluginsPath;
188+ }
189+
190+ if (major != null && major >= 4 && minor != null && minor >= 1 &&
191+ globals.platform.isLinux) {
192+ return globals.fs.path.join (
193+ globals.fsUtils.homeDirPath,
194+ '.local' ,
195+ 'share' ,
196+ 'Google' ,
197+ '$studioAppName $major .$minor ' ,
198+ );
199+ }
200+
164201 return globals.fs.path.join (
165202 globals.fsUtils.homeDirPath,
166203 '.$studioAppName $major .$minor ' ,
@@ -271,22 +308,43 @@ class AndroidStudio implements Comparable<AndroidStudio> {
271308 });
272309 }
273310
274- // Read all $HOME/.AndroidStudio*/system/.home files. There may be several
275- // pointing to the same installation, so we grab only the latest one.
276- if (globals.fsUtils.homeDirPath != null &&
277- globals.fs.directory (globals.fsUtils.homeDirPath).existsSync ()) {
278- final Directory homeDir = globals.fs.directory (globals.fsUtils.homeDirPath);
279- for (final Directory entity in homeDir.listSync (followLinks: false ).whereType <Directory >()) {
280- if (! entity.basename.startsWith ('.AndroidStudio' )) {
281- continue ;
282- }
311+ // Read all $HOME/.AndroidStudio*/system/.home
312+ // or $HOME/.cache/Google/AndroidStudio*/.home files.
313+ // There may be several pointing to the same installation,
314+ // so we grab only the latest one.
315+ final String homeDirPath = globals.fsUtils.homeDirPath;
316+
317+ if (homeDirPath != null && globals.fs.directory (homeDirPath).existsSync ()) {
318+ final Directory homeDir = globals.fs.directory (homeDirPath);
319+
320+ final List <Directory > directoriesToSearch = < Directory > [homeDir];
321+
322+ // >=4.1 has new install location at $HOME/.cache/Google
323+ final String cacheDirPath =
324+ globals.fs.path.join (homeDirPath, '.cache' , 'Google' );
325+
326+ if (globals.fs.isDirectorySync (cacheDirPath)) {
327+ directoriesToSearch.add (globals.fs.directory (cacheDirPath));
328+ }
329+
330+ final List <Directory > entities = < Directory > [];
331+
332+ for (final Directory baseDir in directoriesToSearch) {
333+ final Iterable <Directory > directories =
334+ baseDir.listSync (followLinks: false ).whereType <Directory >();
335+ entities.addAll (directories.where ((Directory directory) =>
336+ _dotHomeStudioVersionMatcher.hasMatch (directory.basename)));
337+ }
338+
339+ for (final Directory entity in entities) {
283340 final AndroidStudio studio = AndroidStudio .fromHomeDot (entity);
284341 if (studio != null && ! _hasStudioAt (studio.directory, newerThan: studio.version)) {
285342 studios.removeWhere ((AndroidStudio other) => other.directory == studio.directory);
286343 studios.add (studio);
287344 }
288345 }
289346 }
347+
290348 // 4.1 has a different location for AndroidStudio installs on Windows.
291349 if (globals.platform.isWindows) {
292350 final File homeDot = globals.fs.file (globals.fs.path.join (
0 commit comments