[url_launcher] Update README to use code excerpts. (#6042)

diff --git a/packages/url_launcher/url_launcher/CHANGELOG.md b/packages/url_launcher/url_launcher/CHANGELOG.md
index e5e98f6..c6e4b9a 100644
--- a/packages/url_launcher/url_launcher/CHANGELOG.md
+++ b/packages/url_launcher/url_launcher/CHANGELOG.md
@@ -1,3 +1,7 @@
+## 6.1.5
+
+* Migrates `README.md` examples to the [`code-excerpt` system](https://github.com/flutter/flutter/wiki/Contributing-to-Plugins-and-Packages#readme-code).
+
 ## 6.1.4
 
 * Adopts new platform interface method for launching URLs.
diff --git a/packages/url_launcher/url_launcher/README.md b/packages/url_launcher/url_launcher/README.md
index 9ef6b5a..e9e4dae 100644
--- a/packages/url_launcher/url_launcher/README.md
+++ b/packages/url_launcher/url_launcher/README.md
@@ -1,3 +1,5 @@
+<?code-excerpt path-base="excerpts/packages/url_launcher_example"?>
+
 # url_launcher
 
 [![pub package](https://img.shields.io/pub/v/url_launcher.svg)](https://pub.dev/packages/url_launcher)
@@ -14,6 +16,7 @@
 
 ### Example
 
+<?code-excerpt "basic.dart (basic-example)"?>
 ``` dart
 import 'package:flutter/material.dart';
 import 'package:url_launcher/url_launcher.dart';
@@ -24,7 +27,7 @@
       const MaterialApp(
         home: Material(
           child: Center(
-            child: RaisedButton(
+            child: ElevatedButton(
               onPressed: _launchUrl,
               child: Text('Show Flutter homepage'),
             ),
@@ -33,8 +36,10 @@
       ),
     );
 
-void _launchUrl() async {
-  if (!await launchUrl(_url)) throw 'Could not launch $_url';
+Future<void> _launchUrl() async {
+  if (!await launchUrl(_url)) {
+    throw 'Could not launch $_url';
+  }
 }
 ```
 
@@ -65,7 +70,10 @@
 element must be added to your manifest as a child of the root element.
 
 Example:
+
+<?code-excerpt "../../android/app/src/main/AndroidManifest.xml (android-queries)" plaster="none"?>
 ``` xml
+<!-- Provide required visibility configuration for API level 30 and above -->
 <queries>
   <!-- If your app checks for SMS support -->
   <intent>
@@ -133,22 +141,37 @@
 encodes query parameters. Using `queryParameters` will result in spaces being
 converted to `+` in many cases.
 
+<?code-excerpt "encoding.dart (encode-query-parameters)"?>
 ```dart
 String? encodeQueryParameters(Map<String, String> params) {
   return params.entries
-      .map((e) => '${Uri.encodeComponent(e.key)}=${Uri.encodeComponent(e.value)}')
+      .map((MapEntry<String, String> e) =>
+          '${Uri.encodeComponent(e.key)}=${Uri.encodeComponent(e.value)}')
       .join('&');
 }
+// ···
+  final Uri emailLaunchUri = Uri(
+    scheme: 'mailto',
+    path: 'smith@example.com',
+    query: encodeQueryParameters(<String, String>{
+      'subject': 'Example Subject & Symbols are allowed!',
+    }),
+  );
 
-final Uri emailLaunchUri = Uri(
-  scheme: 'mailto',
-  path: 'smith@example.com',
-  query: encodeQueryParameters(<String, String>{
-    'subject': 'Example Subject & Symbols are allowed!'
-  }),
+  launchUrl(emailLaunchUri);
+```
+
+Encoding for `sms` is slightly different:
+
+<?code-excerpt "encoding.dart (sms)"?>
+```dart
+final Uri smsLaunchUri = Uri(
+  scheme: 'sms',
+  path: '0118 999 881 999 119 7253',
+  queryParameters: <String, String>{
+    'body': Uri.encodeComponent('Example Subject & Symbols are allowed!'),
+  },
 );
-
-launchUrl(emailLaunchUri);
 ```
 
 ### URLs not handled by `Uri`
@@ -168,14 +191,17 @@
 We recommend checking first whether the directory or file exists before calling `launchUrl`.
 
 Example:
+
+<?code-excerpt "files.dart (file)"?>
 ```dart
-var filePath = '/path/to/file';
+final String filePath = testFile.absolute.path;
 final Uri uri = Uri.file(filePath);
 
-if (await File(uri.toFilePath()).exists()) {
-  if (!await launchUrl(uri)) {
-    throw 'Could not launch $uri';
-  }
+if (!File(uri.toFilePath()).existsSync()) {
+  throw '$uri does not exist!';
+}
+if (!await launchUrl(uri)) {
+  throw 'Could not launch $uri';
 }
 ```
 
diff --git a/packages/url_launcher/url_launcher/example/android/app/src/main/AndroidManifest.xml b/packages/url_launcher/url_launcher/example/android/app/src/main/AndroidManifest.xml
index 5c0d0af..fe01f2f 100644
--- a/packages/url_launcher/url_launcher/example/android/app/src/main/AndroidManifest.xml
+++ b/packages/url_launcher/url_launcher/example/android/app/src/main/AndroidManifest.xml
@@ -7,21 +7,29 @@
   -->
   <uses-permission android:name="android.permission.INTERNET"/>
 
+  <!--#docregion android-queries-->
   <!-- Provide required visibility configuration for API level 30 and above -->
   <queries>
-    <intent>
-      <action android:name="android.intent.action.VIEW" />
-      <data android:scheme="https" />
-    </intent>
-    <intent>
-      <action android:name="android.intent.action.VIEW" />
-      <data android:scheme="tel" />
-    </intent>
+    <!-- If your app checks for SMS support -->
     <intent>
       <action android:name="android.intent.action.VIEW" />
       <data android:scheme="sms" />
     </intent>
+    <!-- If your app checks for call support -->
+    <intent>
+      <action android:name="android.intent.action.VIEW" />
+      <data android:scheme="tel" />
+    </intent>
+    <!--#enddocregion android-queries-->
+    <!-- The "https" scheme is only required for integration tests of this package.
+         It shouldn't be needed in most actual apps, or show up in the README! -->
+    <intent>
+      <action android:name="android.intent.action.VIEW" />
+      <data android:scheme="https" />
+    </intent>
+    <!--#docregion android-queries-->
   </queries>
+  <!--#enddocregion android-queries-->
 
   <application
     android:icon="@mipmap/ic_launcher"
diff --git a/packages/url_launcher/url_launcher/example/build.excerpt.yaml b/packages/url_launcher/url_launcher/example/build.excerpt.yaml
new file mode 100644
index 0000000..c9a9c71
--- /dev/null
+++ b/packages/url_launcher/url_launcher/example/build.excerpt.yaml
@@ -0,0 +1,20 @@
+targets:
+  $default:
+    sources:
+      include:
+        - lib/**
+        - android/app/src/main/**
+        # Some default includes that aren't really used here but will prevent
+        # false-negative warnings:
+        - $package$
+        - lib/$lib$
+      exclude:
+        - '**/.*/**'
+        - '**/build/**'
+        - 'android/app/src/main/res/**'
+    builders:
+      code_excerpter|code_excerpter:
+        enabled: true
+        generate_for:
+          - '**/*.dart'
+          - android/**/*.xml
diff --git a/packages/url_launcher/url_launcher/example/lib/basic.dart b/packages/url_launcher/url_launcher/example/lib/basic.dart
new file mode 100644
index 0000000..987ca21
--- /dev/null
+++ b/packages/url_launcher/url_launcher/example/lib/basic.dart
@@ -0,0 +1,34 @@
+// Copyright 2013 The Flutter Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// Run this example with: flutter run -t lib/basic.dart -d emulator
+
+// This file is used to extract code samples for the README.md file.
+// Run update-excerpts if you modify this file.
+
+// #docregion basic-example
+import 'package:flutter/material.dart';
+import 'package:url_launcher/url_launcher.dart';
+
+final Uri _url = Uri.parse('https://flutter.dev');
+
+void main() => runApp(
+      const MaterialApp(
+        home: Material(
+          child: Center(
+            child: ElevatedButton(
+              onPressed: _launchUrl,
+              child: Text('Show Flutter homepage'),
+            ),
+          ),
+        ),
+      ),
+    );
+
+Future<void> _launchUrl() async {
+  if (!await launchUrl(_url)) {
+    throw 'Could not launch $_url';
+  }
+}
+// #enddocregion basic-example
diff --git a/packages/url_launcher/url_launcher/example/lib/encoding.dart b/packages/url_launcher/url_launcher/example/lib/encoding.dart
new file mode 100644
index 0000000..24c7244
--- /dev/null
+++ b/packages/url_launcher/url_launcher/example/lib/encoding.dart
@@ -0,0 +1,70 @@
+// Copyright 2013 The Flutter Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// Run this example with: flutter run -t lib/encoding.dart -d emulator
+
+// This file is used to extract code samples for the README.md file.
+// Run update-excerpts if you modify this file.
+
+import 'package:flutter/material.dart';
+import 'package:url_launcher/url_launcher.dart';
+
+/// Encode [params] so it produces a correct query string.
+/// Workaround for: https://github.com/dart-lang/sdk/issues/43838
+// #docregion encode-query-parameters
+String? encodeQueryParameters(Map<String, String> params) {
+  return params.entries
+      .map((MapEntry<String, String> e) =>
+          '${Uri.encodeComponent(e.key)}=${Uri.encodeComponent(e.value)}')
+      .join('&');
+}
+// #enddocregion encode-query-parameters
+
+void main() => runApp(
+      MaterialApp(
+        home: Material(
+          child: Column(
+            mainAxisAlignment: MainAxisAlignment.spaceEvenly,
+            children: const <Widget>[
+              ElevatedButton(
+                onPressed: _composeMail,
+                child: Text('Compose an email'),
+              ),
+              ElevatedButton(
+                onPressed: _composeSms,
+                child: Text('Compose a SMS'),
+              ),
+            ],
+          ),
+        ),
+      ),
+    );
+
+void _composeMail() {
+// #docregion encode-query-parameters
+  final Uri emailLaunchUri = Uri(
+    scheme: 'mailto',
+    path: 'smith@example.com',
+    query: encodeQueryParameters(<String, String>{
+      'subject': 'Example Subject & Symbols are allowed!',
+    }),
+  );
+
+  launchUrl(emailLaunchUri);
+// #enddocregion encode-query-parameters
+}
+
+void _composeSms() {
+// #docregion sms
+  final Uri smsLaunchUri = Uri(
+    scheme: 'sms',
+    path: '0118 999 881 999 119 7253',
+    queryParameters: <String, String>{
+      'body': Uri.encodeComponent('Example Subject & Symbols are allowed!'),
+    },
+  );
+// #enddocregion sms
+
+  launchUrl(smsLaunchUri);
+}
diff --git a/packages/url_launcher/url_launcher/example/lib/files.dart b/packages/url_launcher/url_launcher/example/lib/files.dart
new file mode 100644
index 0000000..d484406
--- /dev/null
+++ b/packages/url_launcher/url_launcher/example/lib/files.dart
@@ -0,0 +1,47 @@
+// Copyright 2013 The Flutter Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// Run this example with: flutter run -t lib/files.dart -d linux
+
+// This file is used to extract code samples for the README.md file.
+// Run update-excerpts if you modify this file.
+import 'dart:io';
+
+import 'package:flutter/material.dart';
+import 'package:path/path.dart' as p;
+import 'package:url_launcher/url_launcher.dart';
+
+void main() => runApp(
+      const MaterialApp(
+        home: Material(
+          child: Center(
+            child: ElevatedButton(
+              onPressed: _openFile,
+              child: Text('Open File'),
+            ),
+          ),
+        ),
+      ),
+    );
+
+Future<void> _openFile() async {
+  // Prepare a file within tmp
+  final String tempFilePath = p.joinAll(<String>[
+    ...p.split(Directory.systemTemp.path),
+    'flutter_url_launcher_example.txt'
+  ]);
+  final File testFile = File(tempFilePath);
+  await testFile.writeAsString('Hello, world!');
+// #docregion file
+  final String filePath = testFile.absolute.path;
+  final Uri uri = Uri.file(filePath);
+
+  if (!File(uri.toFilePath()).existsSync()) {
+    throw '$uri does not exist!';
+  }
+  if (!await launchUrl(uri)) {
+    throw 'Could not launch $uri';
+  }
+// #enddocregion file
+}
diff --git a/packages/url_launcher/url_launcher/example/linux/flutter/generated_plugins.cmake b/packages/url_launcher/url_launcher/example/linux/flutter/generated_plugins.cmake
index 1fc8ed3..f16b4c3 100644
--- a/packages/url_launcher/url_launcher/example/linux/flutter/generated_plugins.cmake
+++ b/packages/url_launcher/url_launcher/example/linux/flutter/generated_plugins.cmake
@@ -6,6 +6,9 @@
   url_launcher_linux
 )
 
+list(APPEND FLUTTER_FFI_PLUGIN_LIST
+)
+
 set(PLUGIN_BUNDLED_LIBRARIES)
 
 foreach(plugin ${FLUTTER_PLUGIN_LIST})
@@ -14,3 +17,8 @@
   list(APPEND PLUGIN_BUNDLED_LIBRARIES $<TARGET_FILE:${plugin}_plugin>)
   list(APPEND PLUGIN_BUNDLED_LIBRARIES ${${plugin}_bundled_libraries})
 endforeach(plugin)
+
+foreach(ffi_plugin ${FLUTTER_FFI_PLUGIN_LIST})
+  add_subdirectory(flutter/ephemeral/.plugin_symlinks/${ffi_plugin}/linux plugins/${ffi_plugin})
+  list(APPEND PLUGIN_BUNDLED_LIBRARIES ${${ffi_plugin}_bundled_libraries})
+endforeach(ffi_plugin)
diff --git a/packages/url_launcher/url_launcher/example/pubspec.yaml b/packages/url_launcher/url_launcher/example/pubspec.yaml
index 43b5265..673785e 100644
--- a/packages/url_launcher/url_launcher/example/pubspec.yaml
+++ b/packages/url_launcher/url_launcher/example/pubspec.yaml
@@ -9,6 +9,7 @@
 dependencies:
   flutter:
     sdk: flutter
+  path: ^1.8.0
   url_launcher:
     # When depending on this package from a real application you should use:
     #   url_launcher: ^x.y.z
@@ -18,6 +19,7 @@
     path: ../
 
 dev_dependencies:
+  build_runner: ^2.1.10
   flutter_driver:
     sdk: flutter
   integration_test:
diff --git a/packages/url_launcher/url_launcher/example/windows/flutter/generated_plugins.cmake b/packages/url_launcher/url_launcher/example/windows/flutter/generated_plugins.cmake
index 411af46..88b22e5 100644
--- a/packages/url_launcher/url_launcher/example/windows/flutter/generated_plugins.cmake
+++ b/packages/url_launcher/url_launcher/example/windows/flutter/generated_plugins.cmake
@@ -6,6 +6,9 @@
   url_launcher_windows
 )
 
+list(APPEND FLUTTER_FFI_PLUGIN_LIST
+)
+
 set(PLUGIN_BUNDLED_LIBRARIES)
 
 foreach(plugin ${FLUTTER_PLUGIN_LIST})
@@ -14,3 +17,8 @@
   list(APPEND PLUGIN_BUNDLED_LIBRARIES $<TARGET_FILE:${plugin}_plugin>)
   list(APPEND PLUGIN_BUNDLED_LIBRARIES ${${plugin}_bundled_libraries})
 endforeach(plugin)
+
+foreach(ffi_plugin ${FLUTTER_FFI_PLUGIN_LIST})
+  add_subdirectory(flutter/ephemeral/.plugin_symlinks/${ffi_plugin}/windows plugins/${ffi_plugin})
+  list(APPEND PLUGIN_BUNDLED_LIBRARIES ${${ffi_plugin}_bundled_libraries})
+endforeach(ffi_plugin)
diff --git a/packages/url_launcher/url_launcher/pubspec.yaml b/packages/url_launcher/url_launcher/pubspec.yaml
index e01cd9b..03d0846 100644
--- a/packages/url_launcher/url_launcher/pubspec.yaml
+++ b/packages/url_launcher/url_launcher/pubspec.yaml
@@ -3,7 +3,7 @@
   web, phone, SMS, and email schemes.
 repository: https://github.com/flutter/plugins/tree/main/packages/url_launcher/url_launcher
 issue_tracker: https://github.com/flutter/flutter/issues?q=is%3Aissue+is%3Aopen+label%3A%22p%3A+url_launcher%22
-version: 6.1.4
+version: 6.1.5
 
 environment:
   sdk: ">=2.14.0 <3.0.0"
diff --git a/script/configs/temp_exclude_excerpt.yaml b/script/configs/temp_exclude_excerpt.yaml
index dec99ee..9f14bf2 100644
--- a/script/configs/temp_exclude_excerpt.yaml
+++ b/script/configs/temp_exclude_excerpt.yaml
@@ -18,7 +18,6 @@
 - plugin_platform_interface
 - quick_actions/quick_actions
 - shared_preferences/shared_preferences
-- url_launcher/url_launcher
 - video_player/video_player
 - webview_flutter/webview_flutter
 - webview_flutter_android