snapshot of https://github.com/flutter/samples.git (main, 2026-09-16; blobs > 131072B omitted)
Some checks failed
Main Branch CI / Test Flutter beta on ubuntu-latest (push) Has been skipped
Main Branch CI / Test Flutter stable on ubuntu-latest (push) Has been skipped
Main Branch CI / Test Flutter beta on macos-latest (push) Has been cancelled
Main Branch CI / Test Flutter stable on macos-latest (push) Has been cancelled

This commit is contained in:
upstream-mirror
2026-09-16 01:43:26 +05:00
commit 9ed6a80afa
2886 changed files with 140184 additions and 0 deletions

View File

@@ -0,0 +1,191 @@
// Autogenerated from Pigeon (v1.0.1), do not edit directly.
// See also: https://pub.dev/packages/pigeon
// ignore_for_file: public_member_api_docs, non_constant_identifier_names, avoid_as, unused_import, unnecessary_parenthesis, prefer_null_aware_operators, omit_local_variable_types, unused_shown_name
// @dart = 2.12
import 'dart:async';
import 'dart:typed_data' show Uint8List, Int32List, Int64List, Float64List;
import 'package:flutter/services.dart';
class Book {
String? title;
String? subtitle;
String? author;
String? summary;
String? publishDate;
int? pageCount;
Thumbnail? thumbnail;
Object encode() {
final pigeonMap = <Object?, Object?>{};
pigeonMap['title'] = title;
pigeonMap['subtitle'] = subtitle;
pigeonMap['author'] = author;
pigeonMap['summary'] = summary;
pigeonMap['publishDate'] = publishDate;
pigeonMap['pageCount'] = pageCount;
pigeonMap['thumbnail'] = thumbnail == null ? null : thumbnail!.encode();
return pigeonMap;
}
static Book decode(Object message) {
final pigeonMap = message as Map<Object?, Object?>;
return Book()
..title = pigeonMap['title'] as String?
..subtitle = pigeonMap['subtitle'] as String?
..author = pigeonMap['author'] as String?
..summary = pigeonMap['summary'] as String?
..publishDate = pigeonMap['publishDate'] as String?
..pageCount = pigeonMap['pageCount'] as int?
..thumbnail = pigeonMap['thumbnail'] != null
? Thumbnail.decode(pigeonMap['thumbnail']!)
: null;
}
}
class Thumbnail {
String? url;
Object encode() {
final pigeonMap = <Object?, Object?>{};
pigeonMap['url'] = url;
return pigeonMap;
}
static Thumbnail decode(Object message) {
final pigeonMap = message as Map<Object?, Object?>;
return Thumbnail()..url = pigeonMap['url'] as String?;
}
}
class _FlutterBookApiCodec extends StandardMessageCodec {
const _FlutterBookApiCodec();
@override
void writeValue(WriteBuffer buffer, Object? value) {
if (value is Book) {
buffer.putUint8(128);
writeValue(buffer, value.encode());
} else {
super.writeValue(buffer, value);
}
}
@override
Object? readValueOfType(int type, ReadBuffer buffer) {
switch (type) {
case 128:
return Book.decode(readValue(buffer)!);
default:
return super.readValueOfType(type, buffer);
}
}
}
abstract class FlutterBookApi {
static const MessageCodec<Object?> codec = _FlutterBookApiCodec();
void displayBookDetails(Book book);
static void setup(FlutterBookApi? api) {
{
const channel = BasicMessageChannel<Object?>(
'dev.flutter.pigeon.FlutterBookApi.displayBookDetails', codec);
if (api == null) {
channel.setMessageHandler(null);
} else {
// ignore: avoid_types_on_closure_parameters
channel.setMessageHandler((Object? message) async {
assert(message != null,
'Argument for dev.flutter.pigeon.FlutterBookApi.displayBookDetails was null.');
final List<Object?> args = (message as List<Object?>?)!;
final Book? arg_book = args[0] as Book?;
assert(arg_book != null,
'Argument for dev.flutter.pigeon.FlutterBookApi.displayBookDetails was null, expected non-null Book.');
api.displayBookDetails(arg_book!);
return;
});
}
}
}
}
class _HostBookApiCodec extends StandardMessageCodec {
const _HostBookApiCodec();
@override
void writeValue(WriteBuffer buffer, Object? value) {
if (value is Book) {
buffer.putUint8(128);
writeValue(buffer, value.encode());
} else {
super.writeValue(buffer, value);
}
}
@override
Object? readValueOfType(int type, ReadBuffer buffer) {
switch (type) {
case 128:
return Book.decode(readValue(buffer)!);
default:
return super.readValueOfType(type, buffer);
}
}
}
class HostBookApi {
/// Constructor for [HostBookApi]. The [binaryMessenger] named argument is
/// available for dependency injection. If it is left null, the default
/// BinaryMessenger will be used which routes to the host platform.
HostBookApi({BinaryMessenger? binaryMessenger})
: _binaryMessenger = binaryMessenger;
final BinaryMessenger? _binaryMessenger;
static const MessageCodec<Object?> codec = _HostBookApiCodec();
Future<void> cancel() async {
final channel = BasicMessageChannel<Object?>(
'dev.flutter.pigeon.HostBookApi.cancel', codec,
binaryMessenger: _binaryMessenger);
final Map<Object?, Object?>? replyMap =
await channel.send(null) as Map<Object?, Object?>?;
if (replyMap == null) {
throw PlatformException(
code: 'channel-error',
message: 'Unable to establish connection on channel.',
details: null,
);
} else if (replyMap['error'] != null) {
final error = (replyMap['error'] as Map<Object?, Object?>?)!;
throw PlatformException(
code: (error['code'] as String?)!,
message: error['message'] as String?,
details: error['details'],
);
}
}
Future<void> finishEditingBook(Book arg_book) async {
final BasicMessageChannel<Object?> channel = BasicMessageChannel<Object?>(
'dev.flutter.pigeon.HostBookApi.finishEditingBook', codec,
binaryMessenger: _binaryMessenger);
final Map<Object?, Object?>? replyMap =
await channel.send(<Object>[arg_book]) as Map<Object?, Object?>?;
if (replyMap == null) {
throw PlatformException(
code: 'channel-error',
message: 'Unable to establish connection on channel.',
details: null,
);
} else if (replyMap['error'] != null) {
final Map<Object?, Object?> error =
(replyMap['error'] as Map<Object?, Object?>?)!;
throw PlatformException(
code: (error['code'] as String?)!,
message: error['message'] as String?,
details: error['details'],
);
}
}
}

View File

@@ -0,0 +1,239 @@
// Copyright 2020 The Flutter team. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import 'package:flutter/material.dart';
import 'package:flutter_module_books/api.dart';
void main() => runApp(const MyApp());
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
theme: ThemeData(primaryColor: const Color(0xff6200ee)),
home: const BookDetail(),
);
}
}
typedef BookReceived = void Function(Book book);
class FlutterBookApiHandler extends FlutterBookApi {
FlutterBookApiHandler(this.callback);
final BookReceived callback;
@override
void displayBookDetails(Book book) {
callback(book);
}
}
class BookDetail extends StatefulWidget {
const BookDetail({super.key, this.hostApi, this.flutterApi, this.book});
// These are the outgoing and incoming APIs that are here for injection for
// tests.
final HostBookApi? hostApi;
final FlutterBookApi? flutterApi;
final Book? book;
@override
State<BookDetail> createState() => _BookDetailState();
}
class _BookDetailState extends State<BookDetail> {
Book? book;
late HostBookApi hostApi;
FocusNode textFocusNode = FocusNode();
TextEditingController titleTextController = TextEditingController();
TextEditingController subtitleTextController = TextEditingController();
TextEditingController authorTextController = TextEditingController();
@override
void initState() {
super.initState();
book = widget.book;
// This `HostBookApi` class instance lets us make outgoing calls to the
// platform.
hostApi = widget.hostApi ?? HostBookApi();
// Registering this `FlutterBookApiHandler` class lets us receive incoming
// calls from the platform.
FlutterBookApi.setup(
FlutterBookApiHandler(
// The `FlutterBookApi` just has one method. Just give a closure for that
// method to the handler class.
(book) {
setState(() {
// This book model is what we're going to return to Kotlin eventually.
// Keep it bound to the UI.
this.book = book;
titleTextController.text = book.title ?? '';
titleTextController.addListener(() {
this.book!.title = titleTextController.text;
});
// Subtitle could be null.
subtitleTextController.text = book.subtitle ?? '';
subtitleTextController.addListener(() {
this.book!.subtitle = subtitleTextController.text;
});
authorTextController.text = book.author ?? '';
authorTextController.addListener(() {
this.book!.author = authorTextController.text;
});
});
},
),
);
}
// Not overriding didUpdateWidget because the Android program can't change
// the book given to Flutter on the Android side.
void clear() {
book = null;
// Keep focus if going to the home screen but unfocus if leaving
// the activity.
textFocusNode.unfocus();
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Book Details'),
leading: IconButton(
icon: const Icon(Icons.clear),
// Pressing clear cancels the edit and leaves the activity without
// modification.
onPressed: () {
hostApi.cancel();
clear();
},
),
actions: [
IconButton(
icon: const Icon(Icons.check),
// Pressing save sends the updated book to the platform.
onPressed: book != null
? () {
hostApi.finishEditingBook(book!);
clear();
}
: null,
),
],
),
body: book == null
// Draw a spinner until the platform gives us the book to show details
// for.
? const Center(child: CircularProgressIndicator())
: BookForm(
book: book!,
focusNode: textFocusNode,
authorTextController: authorTextController,
subtitleTextController: subtitleTextController,
titleTextController: titleTextController,
),
);
}
}
class BookForm extends StatelessWidget {
const BookForm({
super.key,
required this.book,
required this.focusNode,
required this.authorTextController,
required this.subtitleTextController,
required this.titleTextController,
});
final Book book;
final FocusNode focusNode;
final TextEditingController titleTextController;
final TextEditingController subtitleTextController;
final TextEditingController authorTextController;
@override
Widget build(BuildContext context) {
return Focus(
focusNode: focusNode,
child: ListView(
padding: const EdgeInsets.all(24),
children: [
TextField(
controller: titleTextController,
decoration: const InputDecoration(
border: OutlineInputBorder(),
filled: true,
hintText: "Title",
labelText: "Title",
),
),
const SizedBox(height: 24),
TextField(
controller: subtitleTextController,
maxLines: 2,
decoration: const InputDecoration(
border: OutlineInputBorder(),
filled: true,
hintText: "Subtitle",
labelText: "Subtitle",
),
),
const SizedBox(height: 24),
TextField(
controller: authorTextController,
decoration: const InputDecoration(
border: OutlineInputBorder(),
filled: true,
hintText: "Author",
labelText: "Author",
),
),
const SizedBox(height: 32),
const Divider(),
Center(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Text(
'${book.pageCount} pages ~ published ${book.publishDate}',
),
),
),
const Divider(),
const SizedBox(height: 32),
if (book.thumbnail?.url != null) ...[
Center(child: Image.network(book.thumbnail!.url!)),
const SizedBox(height: 32),
],
if (book.summary != null) ...[
const Center(
child: Text(
'BOOK DESCRIPTION',
style: TextStyle(
fontSize: 15,
fontWeight: FontWeight.bold,
decoration: TextDecoration.underline,
),
),
),
const SizedBox(height: 12),
Text(
book.summary ?? '',
style: TextStyle(color: Colors.grey.shade600, height: 1.24),
),
],
],
),
);
}
}