Compare commits
3 Commits
af89539293
...
2209ec64e3
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
2209ec64e3 | ||
|
|
2e825bbae2 | ||
|
|
05f56e91cc |
@@ -1,8 +1,10 @@
|
||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<uses-permission android:name="android.permission.INTERNET" />
|
||||
<application
|
||||
android:label="csp2"
|
||||
android:name="${applicationName}"
|
||||
android:icon="@mipmap/ic_launcher">
|
||||
|
||||
<activity
|
||||
android:name=".MainActivity"
|
||||
android:exported="true"
|
||||
|
||||
32
lib/common/theme/app_theme.dart
Normal file
32
lib/common/theme/app_theme.dart
Normal file
@@ -0,0 +1,32 @@
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:google_fonts/google_fonts.dart';
|
||||
|
||||
class AppTheme {
|
||||
static final ThemeData lightTheme = ThemeData(
|
||||
useMaterial3: true,
|
||||
// ColorScheme을 사용하여 전체적인 색상 톤을 설정합니다.
|
||||
colorScheme: ColorScheme.fromSeed(
|
||||
seedColor: Colors.blue, // 버튼 등 강조 색상은 파란색 계열로 유지합니다.
|
||||
brightness: Brightness.light, // 밝은 테마로 설정합니다.
|
||||
background: Colors.white, // 앱의 전체 배경을 흰색으로 지정합니다.
|
||||
surface: Colors.white, // 카드 등 UI 요소의 표면 색을 흰색으로 지정합니다.
|
||||
),
|
||||
// Scaffold의 기본 배경색을 흰색으로 명확하게 지정합니다.
|
||||
scaffoldBackgroundColor: Colors.white,
|
||||
// 폰트 테마를 설정하고, 기본 텍스트 색상을 검은색으로 지정합니다.
|
||||
textTheme: GoogleFonts.hedvigLettersSansTextTheme(
|
||||
ThemeData.light().textTheme,
|
||||
).apply(
|
||||
bodyColor: Colors.black, // 일반 텍스트 색상
|
||||
displayColor: Colors.black, // 제목 등 큰 텍스트 색상
|
||||
),
|
||||
// 앱 바 테마를 흰색 배경, 검은색 아이콘/글씨로 설정합니다.
|
||||
appBarTheme: const AppBarTheme(
|
||||
backgroundColor: Colors.white,
|
||||
foregroundColor: Colors.black,
|
||||
elevation: 0, // 그림자 제거
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
88
lib/common/widgets/upcoming_class_card.dart
Normal file
88
lib/common/widgets/upcoming_class_card.dart
Normal file
@@ -0,0 +1,88 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import '../../home_page.dart'; // CaseStudyPlan 모델을 import 합니다.
|
||||
|
||||
class UpcomingClassCard extends StatelessWidget {
|
||||
final CaseStudyPlan plan;
|
||||
final VoidCallback onTap;
|
||||
|
||||
const UpcomingClassCard({
|
||||
super.key,
|
||||
required this.plan,
|
||||
required this.onTap,
|
||||
});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return SizedBox(
|
||||
width: 300, // 각 항목의 너비를 지정합니다.
|
||||
child: InkWell(
|
||||
onTap: onTap,
|
||||
child: Card(
|
||||
margin: const EdgeInsets.only(right: 12.0), // 항목 간의 간격 조정
|
||||
elevation: 2.0,
|
||||
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(10.0)),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(12.0),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
Expanded(
|
||||
child: Text(
|
||||
plan.planTitle,
|
||||
style: Theme.of(context).textTheme.titleMedium?.copyWith(fontWeight: FontWeight.bold),
|
||||
overflow: TextOverflow.ellipsis,
|
||||
maxLines: 2,
|
||||
),
|
||||
),
|
||||
const SizedBox(width: 8.0),
|
||||
Text(
|
||||
// plan.planTeacher,
|
||||
"",
|
||||
style: Theme.of(context).textTheme.bodySmall?.copyWith(color: Colors.grey[600]),
|
||||
),
|
||||
],
|
||||
),
|
||||
const SizedBox(height: 8.0),
|
||||
if (plan.thumbnail.isNotEmpty)
|
||||
Expanded(
|
||||
child: ClipRRect(
|
||||
borderRadius: BorderRadius.circular(8.0),
|
||||
child: Image.network(
|
||||
plan.thumbnail,
|
||||
width: double.infinity,
|
||||
fit: BoxFit.cover,
|
||||
loadingBuilder: (BuildContext context, Widget child, ImageChunkEvent? loadingProgress) {
|
||||
if (loadingProgress == null) return child;
|
||||
return Center(
|
||||
child: CircularProgressIndicator(
|
||||
value: loadingProgress.expectedTotalBytes != null
|
||||
? loadingProgress.cumulativeBytesLoaded / loadingProgress.expectedTotalBytes!
|
||||
: null,
|
||||
),
|
||||
);
|
||||
},
|
||||
errorBuilder: (BuildContext context, Object exception, StackTrace? stackTrace) {
|
||||
return const Center(child: Icon(Icons.broken_image, color: Colors.grey, size: 50));
|
||||
},
|
||||
),
|
||||
),
|
||||
)
|
||||
else
|
||||
Expanded(
|
||||
child: Container(
|
||||
color: Colors.grey[200],
|
||||
child: const Center(child: Text('No Image', style: TextStyle(color: Colors.grey)))
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -3,6 +3,7 @@ import 'package:http/http.dart' as http;
|
||||
import 'dart:convert';
|
||||
import 'dart:async'; // Timer를 사용하기 위해 추가
|
||||
import 'package:intl/intl.dart';
|
||||
import 'package:csp2/common/widgets/upcoming_class_card.dart';
|
||||
// import 'package:flutter_native_timezone/flutter_native_timezone.dart'; // 주석 처리된 상태 유지
|
||||
import '../plan_page.dart'; // PlanPage import
|
||||
|
||||
@@ -24,7 +25,7 @@ class CaseStudyPlan {
|
||||
return CaseStudyPlan(
|
||||
planId: json['casestudy lesson id'] ?? '아이디 없음',
|
||||
planTitle: json['course_name'] ?? '제목 없음',
|
||||
planTeacher: json['planTeacher'] ?? '',
|
||||
planTeacher: json['planTeacher'] ?? '선생님',
|
||||
thumbnail: json['course_thumbnail'] ?? '',
|
||||
);
|
||||
}
|
||||
@@ -220,17 +221,20 @@ class _HomePageState extends State<HomePage> {
|
||||
final String formattedDate = DateFormat.yMMMMd().format(displayTime);
|
||||
final String formattedTime = DateFormat.jms().format(displayTime);
|
||||
return Container(
|
||||
width: double.infinity,
|
||||
padding: const EdgeInsets.symmetric(horizontal: 16.0, vertical: 12.0),
|
||||
color: Theme.of(context).primaryColor.withAlpha(25),
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context).primaryColor.withAlpha(25),
|
||||
borderRadius: BorderRadius.circular(8.0),
|
||||
),
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center, // 세로 중앙 정렬
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
const Text('Your Local Time', style: TextStyle(fontWeight: FontWeight.bold, fontSize: 16.0)),
|
||||
const SizedBox(height: 6.0),
|
||||
Text('$formattedDate, $formattedTime', style: const TextStyle(fontSize: 18.0, fontWeight: FontWeight.w500)),
|
||||
const SizedBox(height: 4.0),
|
||||
Text('Timezone: $_currentTimeZone', style: TextStyle(fontSize: 13.0, color: Colors.grey[700])),
|
||||
Text('$formattedTime', style: const TextStyle(fontSize: 18.0, fontWeight: FontWeight.w500)),
|
||||
// const SizedBox(height: 4.0),
|
||||
// Text('Timezone: $_currentTimeZone', style: TextStyle(fontSize: 13.0, color: Colors.grey[700])),
|
||||
],
|
||||
),
|
||||
);
|
||||
@@ -238,59 +242,79 @@ class _HomePageState extends State<HomePage> {
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildButtons() {
|
||||
return Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center, // 세로 중앙 정렬
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch, // 버튼이 가로로 꽉 차게 설정
|
||||
children: [
|
||||
Expanded( // 버튼이 할당된 세로 공간을 모두 차지하도록 설정
|
||||
child: ElevatedButton.icon(
|
||||
icon: const Icon(Icons.add_circle_outline, size: 20),
|
||||
label: const Text('Book Class', style: TextStyle(fontSize: 20)),
|
||||
onPressed: () {
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
const SnackBar(content: Text('Book Class 버튼 기능 구현 예정')),
|
||||
);
|
||||
},
|
||||
style: ElevatedButton.styleFrom(
|
||||
backgroundColor: Colors.blue, // 배경색을 파란색으로 설정
|
||||
foregroundColor: Colors.white, // 글자색을 흰색으로 설정
|
||||
padding: const EdgeInsets.symmetric(horizontal: 16.0, vertical: 12.0),
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(8.0),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
// const SizedBox(height: 8.0),
|
||||
// ElevatedButton.icon(
|
||||
// icon: const Icon(Icons.schedule, size: 20),
|
||||
// label: const Text('Schedule', style: TextStyle(fontSize: 14)),
|
||||
// onPressed: () {
|
||||
// ScaffoldMessenger.of(context).showSnackBar(
|
||||
// const SnackBar(content: Text('Schedule 버튼 기능 구현 예정')),
|
||||
// );
|
||||
// },
|
||||
// style: ElevatedButton.styleFrom(
|
||||
// padding: const EdgeInsets.symmetric(vertical: 12.0),
|
||||
// shape: RoundedRectangleBorder(
|
||||
// borderRadius: BorderRadius.circular(8.0),
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildHomeContent() {
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
_buildLocalTimeBar(),
|
||||
Padding(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 16.0, vertical: 12.0),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
||||
children: <Widget>[
|
||||
Expanded(
|
||||
child: ElevatedButton.icon(
|
||||
icon: const Icon(Icons.add_circle_outline, size: 20),
|
||||
label: const Text('Book Class', style: TextStyle(fontSize: 14)),
|
||||
onPressed: () {
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
const SnackBar(content: Text('Book Class 버튼 기능 구현 예정')),
|
||||
);
|
||||
},
|
||||
style: ElevatedButton.styleFrom(
|
||||
padding: const EdgeInsets.symmetric(vertical: 12.0),
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(8.0),
|
||||
),
|
||||
),
|
||||
child: IntrinsicHeight(
|
||||
child: Row(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 1,
|
||||
child: _buildLocalTimeBar(),
|
||||
),
|
||||
),
|
||||
const SizedBox(width: 12.0),
|
||||
Expanded(
|
||||
child: ElevatedButton.icon(
|
||||
icon: const Icon(Icons.schedule, size: 20),
|
||||
label: const Text('Schedule', style: TextStyle(fontSize: 14)),
|
||||
onPressed: () {
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
const SnackBar(content: Text('Schedule 버튼 기능 구현 예정')),
|
||||
);
|
||||
},
|
||||
style: ElevatedButton.styleFrom(
|
||||
padding: const EdgeInsets.symmetric(vertical: 12.0),
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(8.0),
|
||||
),
|
||||
),
|
||||
const SizedBox(width: 12.0),
|
||||
Expanded(
|
||||
flex: 1,
|
||||
child: _buildButtons(),
|
||||
),
|
||||
),
|
||||
],
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
const Padding(
|
||||
padding: EdgeInsets.fromLTRB(16.0, 16.0, 16.0, 8.0), // vertical을 위아래 다르게 조정
|
||||
child: Text('Upcoming Classes', style: TextStyle(fontSize: 20.0, fontWeight: FontWeight.bold)),
|
||||
),
|
||||
Expanded(
|
||||
SizedBox(
|
||||
height: 250, // 가로 리스트의 높이를 지정합니다.
|
||||
child: FutureBuilder<List<CaseStudyPlan>>(
|
||||
future: _caseStudyPlans,
|
||||
builder: (context, snapshot) {
|
||||
@@ -306,79 +330,16 @@ class _HomePageState extends State<HomePage> {
|
||||
} else {
|
||||
final plans = snapshot.data!;
|
||||
return ListView.builder(
|
||||
padding: const EdgeInsets.only(top: 8.0),
|
||||
scrollDirection: Axis.horizontal, // 가로 스크롤로 변경
|
||||
padding: const EdgeInsets.only(left: 16.0, right: 16.0, top: 8.0),
|
||||
itemCount: plans.length,
|
||||
itemBuilder: (context, index) {
|
||||
final plan = plans[index];
|
||||
return InkWell(
|
||||
return UpcomingClassCard(
|
||||
plan: plan,
|
||||
onTap: () {
|
||||
// *** 부모 위젯(MyHomePage)에게 Plan 탭으로 이동하라고 알림 ***
|
||||
// *** PlanPage가 _widgetOptions 리스트에서 두 번째(인덱스 1)라고 가정 ***
|
||||
widget.onNavigateToPlanTab(1); // *** 전달받은 콜백 호출 ***
|
||||
widget.onNavigateToPlanTab(1);
|
||||
},
|
||||
child: Card(
|
||||
margin: const EdgeInsets.symmetric(vertical: 6.0, horizontal: 16.0),
|
||||
elevation: 2.0,
|
||||
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(10.0)),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(12.0),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
Expanded(
|
||||
child: Text(
|
||||
plan.planTitle,
|
||||
style: Theme.of(context).textTheme.titleMedium?.copyWith(fontWeight: FontWeight.bold),
|
||||
overflow: TextOverflow.ellipsis,
|
||||
maxLines: 2,
|
||||
),
|
||||
),
|
||||
const SizedBox(width: 8.0),
|
||||
Text(
|
||||
// plan.planTeacher,
|
||||
"",
|
||||
style: Theme.of(context).textTheme.bodySmall?.copyWith(color: Colors.grey[600]),
|
||||
),
|
||||
],
|
||||
),
|
||||
const SizedBox(height: 8.0),
|
||||
if (plan.thumbnail.isNotEmpty)
|
||||
ClipRRect(
|
||||
borderRadius: BorderRadius.circular(8.0),
|
||||
child: Image.network(
|
||||
plan.thumbnail,
|
||||
height: 150,
|
||||
width: double.infinity,
|
||||
fit: BoxFit.cover,
|
||||
loadingBuilder: (BuildContext context, Widget child, ImageChunkEvent? loadingProgress) {
|
||||
if (loadingProgress == null) return child;
|
||||
return Container(
|
||||
height: 150,
|
||||
color: Colors.grey[200],
|
||||
child: Center(
|
||||
child: CircularProgressIndicator(
|
||||
value: loadingProgress.expectedTotalBytes != null
|
||||
? loadingProgress.cumulativeBytesLoaded / loadingProgress.expectedTotalBytes!
|
||||
: null,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
errorBuilder: (BuildContext context, Object exception, StackTrace? stackTrace) {
|
||||
return Container(height: 150, color: Colors.grey[200], child: const Center(child: Icon(Icons.broken_image, color: Colors.grey, size: 50)));
|
||||
},
|
||||
),
|
||||
)
|
||||
else
|
||||
Container(height: 150, color: Colors.grey[200], child: const Center(child: Text('No Image', style: TextStyle(color: Colors.grey)))),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
// main.dart
|
||||
|
||||
import 'package:csp2/common/theme/app_theme.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
// 새로 만든 페이지 파일들을 import 합니다.
|
||||
@@ -21,10 +22,7 @@ class MyApp extends StatelessWidget {
|
||||
Widget build(BuildContext context) {
|
||||
return MaterialApp(
|
||||
title: 'Case Study',
|
||||
theme: ThemeData(
|
||||
colorScheme: ColorScheme.fromSeed(seedColor: Color(0xFF2005E6)),
|
||||
useMaterial3: true,
|
||||
),
|
||||
theme: AppTheme.lightTheme,
|
||||
home: const MyHomePage(),
|
||||
);
|
||||
}
|
||||
@@ -80,25 +78,24 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
// AppBar의 제목을 현재 탭에 따라 동적으로 변경
|
||||
String appBarTitle = 'Home'; // 기본값
|
||||
if (_selectedIndex == 1) {
|
||||
appBarTitle = 'Plan';
|
||||
}
|
||||
else if (_selectedIndex == 2) {
|
||||
appBarTitle = 'Statistics';
|
||||
}
|
||||
else if (_selectedIndex == 3) {
|
||||
appBarTitle = 'Career';
|
||||
}
|
||||
else if (_selectedIndex == 4) {
|
||||
appBarTitle = 'More';
|
||||
}
|
||||
// String appBarTitle = 'Home'; // 기본값
|
||||
// if (_selectedIndex == 1) {
|
||||
// appBarTitle = 'Plan';
|
||||
// }
|
||||
// else if (_selectedIndex == 2) {
|
||||
// appBarTitle = 'Statistics';
|
||||
// }
|
||||
// else if (_selectedIndex == 3) {
|
||||
// appBarTitle = 'Career';
|
||||
// }
|
||||
// else if (_selectedIndex == 4) {
|
||||
// appBarTitle = 'More';
|
||||
// }
|
||||
|
||||
return Scaffold(
|
||||
appBar: AppBar(
|
||||
toolbarHeight: 40,
|
||||
backgroundColor: Theme.of(context).colorScheme.inversePrimary,
|
||||
title: Text(appBarTitle), // 동적으로 변경된 AppBar 제목\
|
||||
title: Text("Case Study"), // 동적으로 변경된 AppBar 제목\
|
||||
actions: <Widget>[
|
||||
IconButton(
|
||||
icon: const Icon(Icons.notifications),
|
||||
|
||||
@@ -51,11 +51,12 @@ class _PlanPageDetailState extends State<PlanPageDetail> {
|
||||
late int _currentBottomNavIndex;
|
||||
String? _selectedYoutubeUrl;
|
||||
PlanDetailItem? _selectedItem; // <<< 선택된 아이템을 저장할 변수 추가
|
||||
final ScrollController _scrollController = ScrollController(); // 스크롤 컨트롤러 추가
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
_currentBottomNavIndex = 0;
|
||||
_currentBottomNavIndex = 1;
|
||||
}
|
||||
|
||||
@override
|
||||
@@ -124,6 +125,12 @@ class _PlanPageDetailState extends State<PlanPageDetail> {
|
||||
);
|
||||
}
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
_scrollController.dispose(); // 스크롤 컨트롤러 해제
|
||||
super.dispose();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Scaffold(
|
||||
@@ -191,6 +198,7 @@ class _PlanPageDetailState extends State<PlanPageDetail> {
|
||||
final item = details[index];
|
||||
return GestureDetector(
|
||||
onTap: () {
|
||||
_scrollController.jumpTo(0); // 스크롤 맨 위로 이동
|
||||
setState(() {
|
||||
_selectedItem = item;
|
||||
if (item.lessonUrl.isNotEmpty &&
|
||||
@@ -292,6 +300,7 @@ class _PlanPageDetailState extends State<PlanPageDetail> {
|
||||
),
|
||||
Expanded(
|
||||
child: SingleChildScrollView(
|
||||
controller: _scrollController, // 스크롤 컨트롤러 연결
|
||||
padding: const EdgeInsets.all(16.0),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
@@ -337,7 +346,7 @@ class _PlanPageDetailState extends State<PlanPageDetail> {
|
||||
),
|
||||
),
|
||||
IconButton(
|
||||
icon: const Icon(Icons.play_circle_fill, size: 40, color: Colors.red),
|
||||
icon: const Icon(Icons.play_circle_fill, size: 40, color: Colors.blue),
|
||||
onPressed: () {
|
||||
if (_selectedYoutubeUrl != null && _selectedYoutubeUrl!.isNotEmpty) {
|
||||
Navigator.push(
|
||||
|
||||
@@ -6,7 +6,9 @@ import FlutterMacOS
|
||||
import Foundation
|
||||
|
||||
import flutter_inappwebview_macos
|
||||
import path_provider_foundation
|
||||
|
||||
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
|
||||
InAppWebViewFlutterPlugin.register(with: registry.registrar(forPlugin: "InAppWebViewFlutterPlugin"))
|
||||
PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin"))
|
||||
}
|
||||
|
||||
90
pubspec.lock
90
pubspec.lock
@@ -41,6 +41,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.19.1"
|
||||
crypto:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: crypto
|
||||
sha256: "1e445881f28f22d6140f181e07737b22f1e099a5e1ff94b0af2f9e4a463f4855"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.0.6"
|
||||
cupertino_icons:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@@ -57,6 +65,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.3.3"
|
||||
ffi:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: ffi
|
||||
sha256: "289279317b4b16eb2bb7e271abccd4bf84ec9bdcbe999e278a94b804f5630418"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.4"
|
||||
flutter:
|
||||
dependency: "direct main"
|
||||
description: flutter
|
||||
@@ -144,6 +160,14 @@ packages:
|
||||
description: flutter
|
||||
source: sdk
|
||||
version: "0.0.0"
|
||||
google_fonts:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: google_fonts
|
||||
sha256: b1ac0fe2832c9cc95e5e88b57d627c5e68c223b9657f4b96e1487aa9098c7b82
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "6.2.1"
|
||||
http:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@@ -232,6 +256,62 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.9.1"
|
||||
path_provider:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: path_provider
|
||||
sha256: "50c5dd5b6e1aaf6fb3a78b33f6aa3afca52bf903a8a5298f53101fdaee55bbcd"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.5"
|
||||
path_provider_android:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: path_provider_android
|
||||
sha256: d0d310befe2c8ab9e7f393288ccbb11b60c019c6b5afc21973eeee4dda2b35e9
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.2.17"
|
||||
path_provider_foundation:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: path_provider_foundation
|
||||
sha256: "4843174df4d288f5e29185bd6e72a6fbdf5a4a4602717eed565497429f179942"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.4.1"
|
||||
path_provider_linux:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: path_provider_linux
|
||||
sha256: f7a1fe3a634fe7734c8d3f2766ad746ae2a2884abe22e241a8b301bf5cac3279
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.2.1"
|
||||
path_provider_platform_interface:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: path_provider_platform_interface
|
||||
sha256: "88f5779f72ba699763fa3a3b06aa4bf6de76c8e5de842cf6f29e2e06476c2334"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.2"
|
||||
path_provider_windows:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: path_provider_windows
|
||||
sha256: bd6f00dbd873bfb70d0761682da2b3a2c2fccc2b9e84c495821639601d81afe7
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.3.0"
|
||||
platform:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: platform
|
||||
sha256: "5d6b1b0036a5f331ebc77c850ebc8506cbc1e9416c27e59b439f917a902a4984"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.1.6"
|
||||
plugin_platform_interface:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -325,6 +405,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.1.1"
|
||||
xdg_directories:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: xdg_directories
|
||||
sha256: "7a3f37b05d989967cdddcbb571f1ea834867ae2faa29725fd085180e0883aa15"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.1.0"
|
||||
youtube_player_flutter:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@@ -335,4 +423,4 @@ packages:
|
||||
version: "9.1.1"
|
||||
sdks:
|
||||
dart: ">=3.8.1 <4.0.0"
|
||||
flutter: ">=3.24.0"
|
||||
flutter: ">=3.27.0"
|
||||
|
||||
@@ -37,6 +37,7 @@ dependencies:
|
||||
# The following adds the Cupertino Icons font to your application.
|
||||
# Use with the CupertinoIcons class for iOS style icons.
|
||||
cupertino_icons: ^1.0.8
|
||||
google_fonts: ^6.2.1
|
||||
|
||||
dev_dependencies:
|
||||
flutter_test:
|
||||
|
||||
Reference in New Issue
Block a user