Flutter Создание карты с текстом и видео на YouTubeIOS

Программируем под IOS
Ответить
Anonymous
 Flutter Создание карты с текстом и видео на YouTube

Сообщение Anonymous »

Я создаю карту с Flutter, где карта в качестве текстового раздела и раздел видео на YouTube:

/> 1. Когда кнопка полноэкранной кнопки нажата, я хочу, чтобы только видео на YouTube стало полноэкранным горизонтальным. Однако, когда кнопка нажимается, все приложение становится горизонтально полным экраном:

может кто -нибудь сказать мне, в чем проблема в моем коде флаттера?
//main.dart

import 'package:flutter/material.dart';
import 'package:supabase_flutter/supabase_flutter.dart';
import 'features/drills/presentation/pages/drills_home_page.dart';
import 'core/config/supabase_config.dart';

void main() async {
WidgetsFlutterBinding.ensureInitialized();

await Supabase.initialize(url: SupabaseConfig.projectUrl, anonKey: SupabaseConfig.anonKey);

runApp(const TennisDrillsApp());
}

class TennisDrillsApp extends StatelessWidget {
const TennisDrillsApp({super.key});

@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Tennis Drills App',
theme: ThemeData(
colorScheme: ColorScheme.fromSeed(
seedColor: const Color(0xFF339933), // Tennis court green
),
useMaterial3: true,
),
home: const DrillsHomePage(),
debugShowCheckedModeBanner: false,
);
}
}

< /code>
// drills_home_page.dart

import 'package:flutter/material.dart';
import 'package:supabase_flutter/supabase_flutter.dart';
// import '../widgets/drill_card.dart';
import '../widgets/drill_card_with_youtube_video.dart';
import '../../data/repositories/supabase_drill_repository.dart';
import '../../domain/models/drill.dart';

class DrillsHomePage extends StatefulWidget {
const DrillsHomePage({super.key});

@override
State createState() => _DrillsHomePageState();
}

class _DrillsHomePageState extends State {
String _selectedCategory = 'all';
late final SupabaseDrillRepository _drillRepository;
List _drills = [];
bool _isLoading = true;
String? _error;

@override
void initState() {
super.initState();
_drillRepository = SupabaseDrillRepository(Supabase.instance.client);
_loadDrills();
}

Future _loadDrills() async {
try {
setState(() {
_isLoading = true;
_error = null;
});

final drills = await _drillRepository.getDrills();
setState(() {
_drills = drills;
_isLoading = false;
});
} catch (e) {
setState(() {
_error = 'Failed to load drills: ${e.toString()}';
_isLoading = false;
});
}
}

List get filteredDrills {
if (_selectedCategory == 'all') {
return _drills;
}
return _drills.where((drill) => drill.category == _selectedCategory).toList();
}

@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Tennis Drills'),
backgroundColor: Theme.of(context).colorScheme.inversePrimary,
actions: [
// Forehand filter icon
IconButton(
icon: Icon(
Icons.sports_tennis,
color: _selectedCategory == 'forehand' ? Theme.of(context).colorScheme.primary : null,
),
tooltip: 'Forehand Drills',
onPressed: () {
setState(() {
_selectedCategory = _selectedCategory == 'forehand' ? 'all' : 'forehand';
});
},
),
// Backhand filter icon
IconButton(
icon: Transform(
alignment: Alignment.center,
transform: Matrix4.rotationY(3.14), // Flip the icon horizontally
child: Icon(
Icons.sports_tennis,
color: _selectedCategory == 'backhand' ? Theme.of(context).colorScheme.primary : null,
),
),
tooltip: 'Backhand Drills',
onPressed: () {
setState(() {
_selectedCategory = _selectedCategory == 'backhand' ? 'all' : 'backhand';
});
},
),
// Refresh button
IconButton(icon: const Icon(Icons.refresh), tooltip: 'Refresh Drills', onPressed: _loadDrills),
],
),
body: _buildBody(),
);
}

Widget _buildBody() {
if (_isLoading) {
return const Center(child: CircularProgressIndicator());
}

if (_error != null) {
return Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(_error!, style: const TextStyle(color: Colors.red)),
const SizedBox(height: 16),
ElevatedButton(onPressed: _loadDrills, child: const Text('Retry')),
],
),
);
}

if (filteredDrills.isEmpty) {
return const Center(child: Text('No drills found'));
}

return ListView.builder(
itemCount: filteredDrills.length,
itemBuilder: (context, index) {
final drill = filteredDrills[index];
// return DrillCard(drill: drill.toJson());
return DrillCardWithYoutubeVideo(drill: drill.toJson(), videoId: '928wJjWeVyk');
},
);
}
}

< /code>
// drill_card_with_youtube_video.dart

import 'package:flutter/material.dart';
import 'package:youtube_player_flutter/youtube_player_flutter.dart';

class DrillCardWithYoutubeVideo extends StatefulWidget {
final Map drill;
final String videoId;

const DrillCardWithYoutubeVideo({super.key, required this.drill, required this.videoId});

@override
State createState() => _DrillCardWithYoutubeVideoState();
}

class _DrillCardWithYoutubeVideoState extends State {
late YoutubePlayerController _controller;

@override
void initState() {
super.initState();
_controller = YoutubePlayerController(
initialVideoId: widget.videoId,
flags: const YoutubePlayerFlags(autoPlay: false, mute: false),
);
}

@override
void dispose() {
_controller.dispose();
super.dispose();
}

@override
Widget build(BuildContext context) {
return Card(
margin: const EdgeInsets.all(8.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
// Text Section
Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(widget.drill['title'], style: Theme.of(context).textTheme.titleLarge),
const SizedBox(height: 8.0),
Text('Category: ${widget.drill['category']}', style: Theme.of(context).textTheme.bodyMedium),
if (widget.drill['description'] != null) ...[
const SizedBox(height: 8.0),
Text(widget.drill['description'], style: Theme.of(context).textTheme.bodyMedium),
],
],
),
),

// YouTube Video Section
AspectRatio(
aspectRatio: 16 / 9,
child: YoutubePlayer(
controller: _controller,
showVideoProgressIndicator: true,
progressIndicatorColor: Theme.of(context).colorScheme.primary,
progressColors: ProgressBarColors(
playedColor: Theme.of(context).colorScheme.primary,
handleColor: Theme.of(context).colorScheme.primary,
),
),
),
],
),
);
}
}



Подробнее здесь: https://stackoverflow.com/questions/796 ... tube-video
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «IOS»