[Flutter] 메모 12

2020. 12. 29. 00:00Flutter Mobile App/Flutter 메모 앱

반응형

기능추가 : 텍스트 오버플로우, 화면 리사이즈

 

resizeToAvoidBottomInset: false


홈 페이지

[screens/home_page.dart]

 

더보기
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:memo/model/memo.dart';
import 'write_page.dart';
import 'package:memo/repository/db_helper.dart';
import 'view_page.dart';

class HomePage extends StatefulWidget {
  final String title;
  HomePage({Key key, this.title}) : super(key: key);

  @override
  _HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {
  String deleteId = '';

  Future<String> _calculation = Future<String>.delayed(
    Duration(seconds: 2),
    () => 'Data Loaded',
  );

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Column(
        children: <Widget>[
          Padding(
            padding: EdgeInsets.only(left: 20, top: 40, bottom: 20),
            child: Container(
              child: Text(
                '메모',
                style: TextStyle(fontSize: 36, color: Colors.blue),
              ),
              alignment: Alignment.centerLeft,
            ),
          ),
          Expanded(
            child: memoBuilder(context),
          )
        ],
      ),
      floatingActionButton: FloatingActionButton.extended(
        onPressed: () {
          print('[+ 메모 추가 액션버튼] 클릭');
          Navigator.push(
              context, MaterialPageRoute(builder: (context) => WritePage()));
        },
        tooltip: '+',
        label: Text('메모 추가'),
        icon: Icon(Icons.add),
      ),
    );
  }

  Future<List<Memo>> loadMemo() async {
    DBHelper dbHelper = DBHelper();
    return await dbHelper.selectMemos();
  }

  Future<void> deleteMemo(String id) async {
    DBHelper dbHelper = DBHelper();
    return await dbHelper.deleteMemo(id);
  }

  void showAlertDialog(BuildContext context) async {
    await showDialog(
        context: context,
        barrierDismissible: false,
        builder: (BuildContext context) {
          return AlertDialog(
            title: Text('삭제 경고'),
            content: Text('정말 삭제하시겠습니까?\n삭제된 메모는 복구되지 않습니다.'),
            actions: [
              FlatButton(
                child: Text('삭제'),
                onPressed: () {
                  Navigator.pop(context, '삭제');
                  setState(() {
                    deleteMemo(deleteId);
                  });
                  deleteId = '';
                },
              ),
              FlatButton(
                child: Text('취소'),
                onPressed: () {
                  deleteId = '';
                  Navigator.pop(context, '취소');
                },
              )
            ],
          );
        });
  }

  Widget memoBuilder(BuildContext parentContext) {
    return FutureBuilder(
      builder: (context, snapshot) {
        if (!snapshot.hasData || snapshot.data.isEmpty) {
          return Center(
              child: Text(
            '지금 바로 "메모 추가" 버튼을 눌러\n 새 메모를 추가해보세요!',
            style: TextStyle(
              fontSize: 15,
              color: Colors.blueAccent,
            ),
            textAlign: TextAlign.center,
          ));
        } else {
          return ListView.builder(
            itemCount: snapshot.data.length,
            itemBuilder: (context, index) {
              Memo memo = snapshot.data[index];
              return InkWell(
                onTap: () {
                  print('탭 클릭');
                  Navigator.push(
                    parentContext,
                    CupertinoPageRoute(
                        builder: (parentContext) => ViewPage(id: memo.id)),
                  );
                },
                onLongPress: () {
                  print('길게 누름');
                  print(memo.id);
                  deleteId = memo.id;
                  setState(() {
                    showAlertDialog(parentContext);
                  });
                },
                child: Container(
                  height: 90,
                  margin:
                      EdgeInsets.only(left: 20, top: 0, bottom: 15, right: 20),
                  padding:
                      EdgeInsets.only(left: 15, top: 10, bottom: 15, right: 15),
                  alignment: Alignment.center,
                  child: Column(
                    children: [
                      Container(
                        child: Text(
                          memo.title,
                          style: TextStyle(
                              fontSize: 20, fontWeight: FontWeight.w500),
                              overflow: TextOverflow.ellipsis,
                        ),
                        alignment: Alignment.topLeft,
                      ),
                      Container(
                        child: Text(
                          memo.text,
                          style: TextStyle(fontSize: 15),
                          textAlign: TextAlign.left,
                          overflow: TextOverflow.ellipsis,
                        ),
                        alignment: Alignment.topLeft,
                      ),
                      Container(
                        child: Text(
                          '최종 수정 시간 : ${memo.editedTime.split('.')[0]}',
                          style: TextStyle(fontSize: 12),
                        ),
                        alignment: Alignment.bottomRight,
                      ),
                    ],
                  ),
                  decoration: BoxDecoration(
                    color: Colors.white,
                    border: Border.all(color: Colors.blue, width: 1),
                    boxShadow: [BoxShadow(color: Colors.blue, blurRadius: 3)],
                    borderRadius: BorderRadius.circular(12),
                  ),
                ),
              );
            },
          );
        }
      },
      future: loadMemo(),
    );
  }
}

 

작성 페이지

[screens/write_page.dart]

 

더보기
import 'package:flutter/material.dart';
import 'package:memo/model/memo.dart';
import 'package:memo/repository/db_helper.dart';
import 'package:crypto/crypto.dart';
import 'dart:convert';

// ignore: must_be_immutable
class WritePage extends StatelessWidget {
  String title = '';
  String text = '';

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      resizeToAvoidBottomInset: false,
      appBar: AppBar(
        actions: [
          IconButton(
            icon: const Icon(Icons.delete),
            onPressed: () {
              print('삭제 아이콘 클릭');
            },
          ),
          IconButton(
            icon: const Icon(Icons.save),
            onPressed: () {
              print('저장 아이콘 클릭');
              saveDB();
            },
          )
        ],
      ),
      body: Padding(
        padding: EdgeInsets.all(20),
        child: Column(
          children: [
            TextField(
              onChanged: (String title) {
                this.title = title;
              },
              style: TextStyle(fontSize: 30, fontWeight: FontWeight.w500),
              keyboardType: TextInputType.multiline,
              maxLines: null,
              decoration: InputDecoration(hintText: '메모 제목을 입력하세요.'),
            ),
            Padding(
              padding: EdgeInsets.all(10),
            ),
            TextField(
              onChanged: (String text) {
                this.text = text;
              },
              keyboardType: TextInputType.multiline,
              maxLines: null,
              decoration: InputDecoration(hintText: '메모 내용을 입력하세요.'),
            ),
          ],
        ),
      ),
    );
  }

  Future<void> saveDB() async {
    DBHelper dbHelper = DBHelper();
    var memo = Memo(
      id: convertStr2Sha512(DateTime.now().toString()),
      title: this.title,
      text: this.text,
      createdTime: DateTime.now().toString(),
      editedTime: DateTime.now().toString(),
    );
    print('저장하기 시도 ${memo.toString()}');
    await dbHelper.insertMemo(memo);
    print('저장하기');
    print(await dbHelper.selectMemos());
  }

  String convertStr2Sha512(String text) {
    var bytes = utf8.encode(text);
    var digest = sha512.convert(bytes);
    print('Sha512 암호화 $text');
    print(digest);
    return digest.toString();
  }
}

 


SingleChildScrollView

 

뷰 페이지

[screens/view_page.dart]

 

더보기
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:memo/model/memo.dart';
import 'package:memo/repository/db_helper.dart';
import 'edit_page.dart';

class ViewPage extends StatelessWidget {
  ViewPage({Key key, this.id}) : super(key: key);
  final String id;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        actions: [
          IconButton(
            icon: const Icon(Icons.delete),
            onPressed: () {
              print('삭제 아이콘 클릭 : $id');
              //showAlertDialog();
            },
          ),
          IconButton(
            icon: const Icon(Icons.edit),
            onPressed: () {
              print('수정');
              Navigator.push(context,
                  CupertinoPageRoute(builder: (context) => EditPage(id: id)));
            },
          )
        ],
      ),
      body: Padding(padding: EdgeInsets.all(20), child: loadBuilder()),
    );
  }

  Future<List<Memo>> loadMemo(String id) async {
    DBHelper dbHelper = DBHelper();
    return await dbHelper.selectMemo(id);
  }

  loadBuilder() {
    return FutureBuilder<List<Memo>>(
      future: loadMemo(id),
      builder: (context, snapshot) {
        if (!snapshot.hasData || snapshot.data.isEmpty) {
          return Container(
            child: Text('데이터를 불러올 수 없습니다.'),
          );
        } else {
          Memo memo = snapshot.data[0];
          return Column(
            crossAxisAlignment: CrossAxisAlignment.stretch,
            children: [
              SingleChildScrollView(
                child: Text(
                  memo.title,
                  style: TextStyle(fontSize: 30, fontWeight: FontWeight.w500),
                ),
              ),
              Text(
                '메모 생성시간 : ${memo.createdTime.split(".")[0]}',
                style: TextStyle(fontSize: 11),
                textAlign: TextAlign.end,
              ),
              Text(
                '메모 수정시간 : ${memo.editedTime.split(".")[0]}',
                style: TextStyle(fontSize: 11),
                textAlign: TextAlign.end,
              ),
              Padding(
                padding: EdgeInsets.all(10),
              ),
              // Text(memo.text),
              Expanded(
                child: Text(memo.text),
              )
            ],
          );
        }
      },
    );
  }
}
반응형

'Flutter Mobile App > Flutter 메모 앱' 카테고리의 다른 글

[Flutter] 메모 11  (0) 2020.12.28
[Flutter] 메모 10  (0) 2020.12.28
[Flutter] 메모 9  (0) 2020.12.28
[Flutter] 메모 8  (0) 2020.12.27
[Flutter] 메모 7  (0) 2020.12.27