나무야3
|
Before Width: | Height: | Size: 1.5 MiB |
|
Before Width: | Height: | Size: 1.4 MiB |
|
Before Width: | Height: | Size: 1.5 MiB |
|
Before Width: | Height: | Size: 1.5 MiB |
|
Before Width: | Height: | Size: 1.4 MiB |
|
Before Width: | Height: | Size: 1.4 MiB |
|
Before Width: | Height: | Size: 1.4 MiB |
|
Before Width: | Height: | Size: 1.4 MiB |
|
Before Width: | Height: | Size: 1.5 MiB |
BIN
assets/images/Main_Back.webp
Normal file
|
After Width: | Height: | Size: 1.0 MiB |
|
Before Width: | Height: | Size: 342 KiB |
|
Before Width: | Height: | Size: 22 KiB |
|
Before Width: | Height: | Size: 23 KiB |
|
Before Width: | Height: | Size: 28 KiB |
|
Before Width: | Height: | Size: 14 KiB |
|
Before Width: | Height: | Size: 14 KiB |
|
Before Width: | Height: | Size: 18 KiB |
|
Before Width: | Height: | Size: 15 KiB |
|
Before Width: | Height: | Size: 35 KiB |
|
Before Width: | Height: | Size: 20 KiB |
@@ -5,24 +5,29 @@ class Assets {
|
|||||||
static const String audio001 = 'assets/audio/001.wav';
|
static const String audio001 = 'assets/audio/001.wav';
|
||||||
static const String audio002 = 'assets/audio/002.wav';
|
static const String audio002 = 'assets/audio/002.wav';
|
||||||
static const String audio003 = 'assets/audio/003.wav';
|
static const String audio003 = 'assets/audio/003.wav';
|
||||||
static const String images001 = 'assets/images/001.jpg';
|
static const String goSubsetsButton01 = 'assets/images/go_subsets/Button_01.webp';
|
||||||
static const String images002 = 'assets/images/002.jpg';
|
static const String goSubsetsButton02 = 'assets/images/go_subsets/Button_02.webp';
|
||||||
static const String images003 = 'assets/images/003.jpg';
|
static const String goSubsetsButton03 = 'assets/images/go_subsets/Button_03.webp';
|
||||||
static const String images004 = 'assets/images/004.jpg';
|
static const String goSubsetsButton04 = 'assets/images/go_subsets/Button_04.webp';
|
||||||
static const String images005 = 'assets/images/005.jpg';
|
static const String goSubsetsButton05 = 'assets/images/go_subsets/Button_05.webp';
|
||||||
static const String images006 = 'assets/images/006.jpg';
|
static const String goSubsetsButton06 = 'assets/images/go_subsets/Button_06.webp';
|
||||||
static const String images007 = 'assets/images/007.jpg';
|
static const String goSubsetsButton07 = 'assets/images/go_subsets/Button_07.webp';
|
||||||
static const String images008 = 'assets/images/008.jpg';
|
static const String goSubsetsButton08 = 'assets/images/go_subsets/Button_08.webp';
|
||||||
static const String images009 = 'assets/images/009.jpg';
|
static const String goSubsetsButton09 = 'assets/images/go_subsets/Button_09.webp';
|
||||||
static const String imagesBackground = 'assets/images/background.jpg';
|
static const String imagesMainBack = 'assets/images/Main_Back.webp';
|
||||||
static const String imagesSwith01 = 'assets/images/swith01.png';
|
static const String subsetsSub01 = 'assets/images/subsets/Sub_01.webp';
|
||||||
static const String imagesSwith02 = 'assets/images/swith02.png';
|
static const String subsetsSub02 = 'assets/images/subsets/Sub_02.webp';
|
||||||
static const String imagesSwith03 = 'assets/images/swith03.png';
|
static const String subsetsSub03 = 'assets/images/subsets/Sub_03.webp';
|
||||||
static const String imagesSwith04 = 'assets/images/swith04.png';
|
static const String subsetsSub04 = 'assets/images/subsets/Sub_04.webp';
|
||||||
static const String imagesSwith05 = 'assets/images/swith05.png';
|
static const String subsetsSub05 = 'assets/images/subsets/Sub_05.webp';
|
||||||
static const String imagesSwith06 = 'assets/images/swith06.png';
|
static const String subsetsSub06 = 'assets/images/subsets/Sub_06.webp';
|
||||||
static const String imagesSwith07 = 'assets/images/swith07.png';
|
static const String subsetsSub07 = 'assets/images/subsets/Sub_07.webp';
|
||||||
static const String imagesSwith08 = 'assets/images/swith08.png';
|
static const String subsetsSub08 = 'assets/images/subsets/Sub_08.webp';
|
||||||
static const String imagesSwith09 = 'assets/images/swith09.png';
|
static const String subsetsSub09 = 'assets/images/subsets/Sub_09.webp';
|
||||||
|
static const String uiUI5minus = 'assets/images/ui/UI_5minus.webp';
|
||||||
|
static const String uiUI5plus = 'assets/images/ui/UI_5plus.webp';
|
||||||
|
static const String uiUIBack = 'assets/images/ui/UI_Back.webp';
|
||||||
|
static const String uiUIPlay = 'assets/images/ui/UI_Play.webp';
|
||||||
|
static const String uiUIReplay = 'assets/images/ui/UI_Replay.webp';
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,8 +1,11 @@
|
|||||||
|
import 'dart:io';
|
||||||
|
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter/services.dart';
|
||||||
import 'package:poet/poet_screen.dart';
|
import 'package:poet/poet_screen.dart';
|
||||||
|
|
||||||
void main() {
|
void main() {
|
||||||
|
WidgetsFlutterBinding.ensureInitialized();
|
||||||
runApp(const MyApp());
|
runApp(const MyApp());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -18,7 +21,41 @@ class MyApp extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class PoetStudyScreen extends StatelessWidget {
|
class PoetStudyScreen extends StatefulWidget {
|
||||||
|
@override
|
||||||
|
_PoetStudyScreenState createState() => _PoetStudyScreenState();
|
||||||
|
}
|
||||||
|
|
||||||
|
class _PoetStudyScreenState extends State<PoetStudyScreen>
|
||||||
|
with WidgetsBindingObserver {
|
||||||
|
@override
|
||||||
|
void initState() {
|
||||||
|
super.initState();
|
||||||
|
WidgetsBinding.instance.addObserver(this);
|
||||||
|
_setSystemUIOverlayStyle();
|
||||||
|
}
|
||||||
|
|
||||||
|
void _setSystemUIOverlayStyle() {
|
||||||
|
if (Platform.isAndroid) {
|
||||||
|
SystemChrome.setEnabledSystemUIMode(SystemUiMode.immersiveSticky);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void dispose() {
|
||||||
|
WidgetsBinding.instance.removeObserver(this);
|
||||||
|
// When the main screen is disposed, restore the system UI
|
||||||
|
SystemChrome.setEnabledSystemUIMode(SystemUiMode.edgeToEdge);
|
||||||
|
super.dispose();
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void didChangeAppLifecycleState(AppLifecycleState state) {
|
||||||
|
if (state == AppLifecycleState.resumed) {
|
||||||
|
_setSystemUIOverlayStyle();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return Scaffold(
|
return Scaffold(
|
||||||
@@ -27,7 +64,7 @@ class PoetStudyScreen extends StatelessWidget {
|
|||||||
// Background Image
|
// Background Image
|
||||||
Positioned.fill(
|
Positioned.fill(
|
||||||
child: Image.asset(
|
child: Image.asset(
|
||||||
'assets/images/background.jpg',
|
'assets/images/Main_Back.webp',
|
||||||
fit: BoxFit.cover,
|
fit: BoxFit.cover,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
@@ -66,9 +103,6 @@ class PoetStudyScreen extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Widget _buildGridItem(BuildContext context, int index) {
|
Widget _buildGridItem(BuildContext context, int index) {
|
||||||
double screenWidth = MediaQuery.of(context).size.width;
|
|
||||||
String imageName = 'swith${(index + 1).toString().padLeft(2, '0')}';
|
|
||||||
|
|
||||||
return GestureDetector(
|
return GestureDetector(
|
||||||
onTap: () {
|
onTap: () {
|
||||||
Navigator.push(
|
Navigator.push(
|
||||||
@@ -80,25 +114,13 @@ class PoetStudyScreen extends StatelessWidget {
|
|||||||
);
|
);
|
||||||
},
|
},
|
||||||
child: Container(
|
child: Container(
|
||||||
decoration: BoxDecoration(
|
|
||||||
color: Colors.white,
|
|
||||||
borderRadius: BorderRadius.circular(10),
|
|
||||||
boxShadow: [
|
|
||||||
BoxShadow(
|
|
||||||
color: Colors.black.withOpacity(0.1),
|
|
||||||
spreadRadius: 1,
|
|
||||||
blurRadius: 5,
|
|
||||||
offset: const Offset(0, 3),
|
|
||||||
),
|
|
||||||
],
|
|
||||||
),
|
|
||||||
child: Column(
|
child: Column(
|
||||||
mainAxisAlignment: MainAxisAlignment.center,
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
children: [
|
children: [
|
||||||
Image.asset(
|
Image.asset(
|
||||||
'assets/images/$imageName.png',
|
'assets/images/go_subsets/Button_${(index + 1).toString().padLeft(2, '0')}.webp',
|
||||||
width: screenWidth * 0.25,
|
width: 325,
|
||||||
height: screenWidth * 0.25,
|
height: 325,
|
||||||
fit: BoxFit.contain,
|
fit: BoxFit.contain,
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
|
|||||||
@@ -13,7 +13,7 @@ class PoetScreen extends StatefulWidget {
|
|||||||
State<PoetScreen> createState() => _PoetScreenState();
|
State<PoetScreen> createState() => _PoetScreenState();
|
||||||
}
|
}
|
||||||
|
|
||||||
class _PoetScreenState extends State<PoetScreen> {
|
class _PoetScreenState extends State<PoetScreen> with WidgetsBindingObserver {
|
||||||
late String _backgroundImage;
|
late String _backgroundImage;
|
||||||
final AudioPlayer _audioPlayer = AudioPlayer();
|
final AudioPlayer _audioPlayer = AudioPlayer();
|
||||||
bool _isPlaying = false;
|
bool _isPlaying = false;
|
||||||
@@ -25,11 +25,11 @@ class _PoetScreenState extends State<PoetScreen> {
|
|||||||
@override
|
@override
|
||||||
void initState() {
|
void initState() {
|
||||||
super.initState();
|
super.initState();
|
||||||
if (Platform.isAndroid) {
|
WidgetsBinding.instance.addObserver(this);
|
||||||
SystemChrome.setEnabledSystemUIMode(SystemUiMode.immersiveSticky);
|
_setSystemUIOverlayStyle();
|
||||||
}
|
|
||||||
_backgroundImage =
|
_backgroundImage =
|
||||||
'assets/images/00${(widget.selectedIndex + 1).toString()}.jpg';
|
'assets/images/subsets/Sub_${(widget.selectedIndex + 1).toString().padLeft(2, '0')}.webp';
|
||||||
_source = AssetSource('audio/00${(widget.selectedIndex + 1).toString()}.wav');
|
_source = AssetSource('audio/00${(widget.selectedIndex + 1).toString()}.wav');
|
||||||
|
|
||||||
_audioPlayer.onPlayerStateChanged.listen((state) {
|
_audioPlayer.onPlayerStateChanged.listen((state) {
|
||||||
@@ -66,6 +66,19 @@ class _PoetScreenState extends State<PoetScreen> {
|
|||||||
_setAudio();
|
_setAudio();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void _setSystemUIOverlayStyle() {
|
||||||
|
if (Platform.isAndroid) {
|
||||||
|
SystemChrome.setEnabledSystemUIMode(SystemUiMode.immersiveSticky);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void didChangeAppLifecycleState(AppLifecycleState state) {
|
||||||
|
if (state == AppLifecycleState.resumed) {
|
||||||
|
_setSystemUIOverlayStyle();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Future<void> _setAudio() async {
|
Future<void> _setAudio() async {
|
||||||
try {
|
try {
|
||||||
await _audioPlayer.setSource(_source);
|
await _audioPlayer.setSource(_source);
|
||||||
@@ -77,6 +90,7 @@ class _PoetScreenState extends State<PoetScreen> {
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
void dispose() {
|
void dispose() {
|
||||||
|
WidgetsBinding.instance.removeObserver(this);
|
||||||
if (Platform.isAndroid) {
|
if (Platform.isAndroid) {
|
||||||
SystemChrome.setEnabledSystemUIMode(SystemUiMode.edgeToEdge);
|
SystemChrome.setEnabledSystemUIMode(SystemUiMode.edgeToEdge);
|
||||||
}
|
}
|
||||||
@@ -110,11 +124,13 @@ class _PoetScreenState extends State<PoetScreen> {
|
|||||||
Row(
|
Row(
|
||||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||||
children: [
|
children: [
|
||||||
_buildCircularButton(Icons.arrow_back, () {
|
_buildCircularImageButton('assets/images/ui/UI_Back.webp', () {
|
||||||
// 이 버튼을 누르면 이전 화면으로 돌아갑니다.
|
// 이 버튼을 누르면 이전 화면으로 돌아갑니다.
|
||||||
Navigator.pop(context);
|
Navigator.pop(context);
|
||||||
}, size: 50, iconSize: 25),
|
}, size: 50, imageSize: 25),
|
||||||
_buildCircularButton(Icons.refresh, () {}, size: 50, iconSize: 25),
|
_buildCircularImageButton('assets/images/ui/UI_Replay.webp', () {
|
||||||
|
// Refresh action here
|
||||||
|
}, size: 50, imageSize: 25),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
|
|
||||||
@@ -157,12 +173,26 @@ class _PoetScreenState extends State<PoetScreen> {
|
|||||||
Row(
|
Row(
|
||||||
mainAxisAlignment: MainAxisAlignment.center,
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
children: [
|
children: [
|
||||||
_buildCircularButton(Icons.replay_5, () {
|
_buildCircularImageButton('assets/images/ui/UI_5minus.webp', () {
|
||||||
final newPosition = _position - const Duration(seconds: 5);
|
final newPosition = _position - const Duration(seconds: 5);
|
||||||
_audioPlayer.seek(newPosition > Duration.zero ? newPosition : Duration.zero);
|
_audioPlayer.seek(newPosition > Duration.zero ? newPosition : Duration.zero);
|
||||||
}),
|
}),
|
||||||
const SizedBox(width: 16),
|
const SizedBox(width: 16),
|
||||||
_buildCircularButton(_isPlaying ? Icons.pause : Icons.play_arrow, () {
|
_buildPlayPauseButton(),
|
||||||
|
const SizedBox(width: 16),
|
||||||
|
_buildCircularImageButton('assets/images/ui/UI_5plus.webp', () {
|
||||||
|
final newPosition = _position + const Duration(seconds: 5);
|
||||||
|
_audioPlayer.seek(newPosition < _duration ? newPosition : _duration);
|
||||||
|
}),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
],
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _buildPlayPauseButton() {
|
||||||
|
return GestureDetector(
|
||||||
|
onTap: () {
|
||||||
if (_isPlaying) {
|
if (_isPlaying) {
|
||||||
_audioPlayer.pause();
|
_audioPlayer.pause();
|
||||||
} else {
|
} else {
|
||||||
@@ -172,15 +202,47 @@ class _PoetScreenState extends State<PoetScreen> {
|
|||||||
_audioPlayer.resume();
|
_audioPlayer.resume();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}),
|
},
|
||||||
const SizedBox(width: 16),
|
child: Container(
|
||||||
_buildCircularButton(Icons.forward_5, () {
|
width: 80,
|
||||||
final newPosition = _position + const Duration(seconds: 5);
|
height: 80,
|
||||||
_audioPlayer.seek(newPosition < _duration ? newPosition : _duration);
|
decoration: BoxDecoration(
|
||||||
}),
|
color: const Color(0xFFF07B41),
|
||||||
],
|
shape: BoxShape.circle,
|
||||||
|
border: Border.all(color: Colors.white, width: 2),
|
||||||
|
),
|
||||||
|
child: Center(
|
||||||
|
child: _isPlaying
|
||||||
|
? const Icon(Icons.pause, color: Colors.white, size: 50)
|
||||||
|
: Image.asset(
|
||||||
|
'assets/images/ui/UI_Play.webp',
|
||||||
|
width: 50,
|
||||||
|
height: 50,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _buildCircularImageButton(String imagePath, VoidCallback onPressed, {double size = 80, double imageSize = 50}) {
|
||||||
|
return GestureDetector(
|
||||||
|
onTap: onPressed,
|
||||||
|
child: Container(
|
||||||
|
width: size,
|
||||||
|
height: size,
|
||||||
|
decoration: BoxDecoration(
|
||||||
|
color: const Color(0xFFF07B41),
|
||||||
|
shape: BoxShape.circle,
|
||||||
|
border: Border.all(color: Colors.white, width: 2),
|
||||||
|
),
|
||||||
|
child: Center(
|
||||||
|
child: Image.asset(
|
||||||
|
imagePath,
|
||||||
|
width: imageSize,
|
||||||
|
height: imageSize,
|
||||||
|
),
|
||||||
|
),
|
||||||
),
|
),
|
||||||
],
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -196,21 +258,5 @@ class _PoetScreenState extends State<PoetScreen> {
|
|||||||
].join(':');
|
].join(':');
|
||||||
}
|
}
|
||||||
|
|
||||||
// 원형 버튼을 만드는 헬퍼 함수
|
|
||||||
Widget _buildCircularButton(IconData icon, VoidCallback onPressed, {double size = 80, double iconSize = 50}) {
|
|
||||||
return Container(
|
|
||||||
width: size,
|
|
||||||
height: size,
|
|
||||||
decoration: BoxDecoration(
|
|
||||||
color: const Color(0xFFF07B41),
|
|
||||||
shape: BoxShape.circle,
|
|
||||||
border: Border.all(color: Colors.white, width: 2),
|
|
||||||
),
|
|
||||||
child: IconButton(
|
|
||||||
onPressed: onPressed,
|
|
||||||
icon: Icon(icon, color: Colors.white),
|
|
||||||
iconSize: iconSize,
|
|
||||||
),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
@@ -58,7 +58,10 @@ flutter:
|
|||||||
# the material Icons class.
|
# the material Icons class.
|
||||||
uses-material-design: true
|
uses-material-design: true
|
||||||
assets:
|
assets:
|
||||||
- assets/images/ # 이 경로가 꼭 포함되어야 합니다.
|
- assets/images/
|
||||||
|
- assets/images/go_subsets/
|
||||||
|
- assets/images/subsets/
|
||||||
|
- assets/images/ui/
|
||||||
- assets/icons/
|
- assets/icons/
|
||||||
- assets/audio/
|
- assets/audio/
|
||||||
# To add assets to your application, add an assets section, like this:
|
# To add assets to your application, add an assets section, like this:
|
||||||
|
|||||||