Files
bini-google-tv/flutter_app/lib/widgets/weather_widget.dart
2026-01-24 19:41:19 +09:00

87 lines
2.6 KiB
Dart

import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import 'package:flutter/foundation.dart';
import '../config/api_config.dart';
import '../models/weather_info.dart';
import '../services/weather_service.dart';
class WeatherWidget extends StatelessWidget {
const WeatherWidget({super.key});
@override
Widget build(BuildContext context) {
return FutureBuilder<WeatherInfo>(
future: Provider.of<WeatherService>(
context,
listen: false,
).fetchWeather(),
builder: (context, snapshot) {
if (snapshot.connectionState == ConnectionState.waiting) {
return const Center(
child: SizedBox(
width: 20,
height: 20,
child: CircularProgressIndicator(strokeWidth: 2),
),
);
}
if (snapshot.hasError) {
return const Text(
'Weather Unavailable',
style: TextStyle(color: Colors.white54),
);
}
if (!snapshot.hasData) {
return const SizedBox.shrink();
}
final weather = snapshot.data!;
// Assuming OpenWeatherMap icon format
final iconUrl = (ApiConfig.useMockData || kIsWeb)
? null
: (weather.icon.isNotEmpty
? "http://openweathermap.org/img/wn/${weather.icon}@2x.png"
: null);
return Row(
mainAxisSize: MainAxisSize.min,
children: [
if (iconUrl != null)
Image.network(
iconUrl,
width: 50,
height: 50,
errorBuilder: (_, __, ___) =>
const Icon(Icons.wb_sunny, color: Colors.amber),
)
else
const Icon(Icons.wb_sunny, color: Colors.amber, size: 40),
const SizedBox(width: 12),
Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(
'${weather.temperature.round()}°C',
style: Theme.of(context).textTheme.headlineSmall?.copyWith(
color: Colors.white,
fontWeight: FontWeight.bold,
),
),
Text(
'${weather.city} · ${weather.description}',
style: Theme.of(
context,
).textTheme.bodyMedium?.copyWith(color: Colors.white70),
),
],
),
],
);
},
);
}
}