android flutter教程,Android开发 学习Flutter 入门

Android开发 学习Flutter 入门

一、前言

最近项目准备用Flutter混合开发,写写学习的笔记吧,学习Flutter首先需要了解Dart语言,(当然安全上网推荐一个Chrome插件(SetupVpn)),了解Dart相关语法之后,可以到Flutter中文网学习Flutter啦。

二、Flutter 环境搭建

Flutter中文网有详细的教程,我在Mac和Windows上都已经成功安装。

Flutter SDK 获取

去flutter官网下载其最新可用的安装包,转到下载页 。下载后将其解压,当前目录将为环境变量需要配置的。

ded8d67a2678

image.png

mac 环境变量设置:

alias br="flutter packages pub run build_runner build" # br 快捷键

alias rmlock="rm -rf /Users/ningzhen942/app/flutter/bin/chche/lockfile" #删除lockfile 快捷键

export PATH=/Users/ningzhen942/app/flutter/bin:$PATH

export PUB_HOSTED_URL=https://pub.flutter-io.cn

export FLUTTER_STORAGE_BASE_URL=https://storage.flutter-io.cn

ded8d67a2678

image.png

配置好环境变量 运行flutter --version 查看版本

ded8d67a2678

image.png

运行 flutter doctor 查看环境状态

ded8d67a2678

image.png

三、Flutter 工程目录结构

ded8d67a2678

四、Flutter Widget 与Android 控件联想

ded8d67a2678

image.png

五、Demo(ListView)

ded8d67a2678

168336246614882_result.gif

import 'package:flutter/foundation.dart';

import 'package:flutter/material.dart';

import 'package:vscodeflutter/home.dart';

import 'package:vscodeflutter/muti_phote_page.dart';

import 'package:vscodeflutter/phote_view_page.dart';

import 'package:vscodeflutter/widght/gradient_text.dart';

import 'package:cached_network_image/cached_network_image.dart';

void main() {

runApp(new MyApp(

items: new List.generate(1000, (i) {

if (i % 8 == 0) {

return new HeadingItem("Heading I am No.$i");

} else if (i % 8 == 1) {

return new ImageItem(

"https://ss2.bdstatic.com/70cFvnSh_Q1YnxGkpoWK1HF6hhy/it/u=2572170802,3058063046&fm=26&gp=0.jpg",

"Message body $i");

} else if (i % 8 == 2) {

List urls = new List.generate(8, (i) {

return "https://ss2.bdstatic.com/70cFvnSh_Q1YnxGkpoWK1HF6hhy/it/u=3806557979,3233516071&fm=27&gp=0.jpg";

});

return new ListImageItem(urls, "多图片浏览");

} else {

return new MessageItem("Sender $i", "Message body $i");

}

}),

));

}

class MyApp extends StatelessWidget {

final List items;

MyApp({Key key, @required this.items}) : super(key: key);

@override

Widget build(BuildContext context) {

final title = 'Flutter List';

return new MaterialApp(

title: title,

home: new Scaffold(

appBar: new AppBar(

title: new Text(title),

backgroundColor: Colors.green,

),

body: new ListView.builder(

// Let the ListView know how many items it needs to build

itemCount: items.length,

// Provide a builder function. This is where the magic happens! We'll

// convert each item into a Widget based on the type of item it is.

itemBuilder: (context, index) {

final item = items[index];

if (item is HeadingItem) {

return getTitleItem(item, context);

} else if (item is MessageItem) {

return new ListTile(

title: new Text(item.sender),

subtitle: new Text(item.body),

);

} else if (item is ImageItem) {

return getImageItem(item, context);

} else if (item is ListImageItem) {

return new Container(

height: 220,

width: double.infinity,

padding: EdgeInsets.fromLTRB(10, 10, 0, 10),

child: ListView.builder(

itemBuilder: (context, index) {

return getListItem(context, item, index);

},

itemCount: item.urls.length,

scrollDirection: Axis.horizontal,

));

}

},

),

),

);

}

ListTile getTitleItem(HeadingItem item, BuildContext context) {

return new ListTile(

title: new GestureDetector(

child: new GradientText(

item.heading,

textAlign: TextAlign.left,

gradient: LinearGradient(colors: [Colors.redAccent, Colors.green]),

style: TextStyle(

fontSize: 30.0,

),

),

onTap: () {

Navigator.push(

context,

new MaterialPageRoute(builder: (context) => new HomePage()),

);

},

));

}

Widget getImageItem(ImageItem item, BuildContext context) {

return new Container(

height: 100,

margin: EdgeInsets.only(left: 10),

child: Stack(

children: [

new GestureDetector(

/*child: ClipRRect(

borderRadius: BorderRadius.circular(10),

child: new CachedNetworkImage(

imageUrl: item.url,

height: 100,

),

),*/

child: new ClipOval(

child: new CachedNetworkImage(

imageUrl: item.url,

height: 100,

),

),

onTap: () {

Navigator.push(

context,

new MaterialPageRoute(

builder: (context) => new PhoteViewPage(item.url)));

},

),

],

),

);

}

Container getListItem(BuildContext context, ListImageItem item, int index) {

return new Container(

width: 220,

height: 220,

padding: new EdgeInsets.only(right: 10),

child: GestureDetector(

onTap: () {

Navigator.push(

context,

new MaterialPageRoute(

builder: (context) => new MutiPhotePage(item.urls, index)));

},

child: ClipRRect(

borderRadius: BorderRadius.circular(6),

child: new CachedNetworkImage(

imageUrl: item.urls[index],

fit: BoxFit.cover,

placeholder: (context, url) => new CircularProgressIndicator(),

errorWidget: (context, url, error) => new Icon(Icons.error),

),

),

));

}

}

// The base class for the different types of items the List can contain

abstract class ListItem {}

// A ListItem that contains data to display a heading

class HeadingItem implements ListItem {

final String heading;

HeadingItem(this.heading);

}

// A ListItem that contains data to display a message

class MessageItem implements ListItem {

final String sender;

final String body;

MessageItem(this.sender, this.body);

}

// A ListItem that contains data to display a message

class ImageItem implements ListItem {

final String url;

final String title;

ImageItem(this.url, this.title);

}

// A ListItem that contains data to display a message

class ListImageItem implements ListItem {

final List urls;

final String title;

ListImageItem(this.urls, this.title);

}

六、Demo直接贴代码(图片浏览放大)

首先在pubspec.yaml引用phote_view 和网络图片加载库

ded8d67a2678

image.png

#https://github.com/renefloor/flutter_cached_network_image

cached_network_image: ^0.7.0

#https://github.com/renancaraujo/photo_view

photo_view: ^0.2.2

import 'package:flutter/material.dart';

import 'package:photo_view/photo_view.dart';

import 'package:cached_network_image/cached_network_image.dart';

// ignore: must_be_immutable

class PhoteViewPage extends StatefulWidget {

String url;

PhoteViewPage(this.url);

@override

PhoteViewPageState createState() => new PhoteViewPageState(this.url);

}

class PhoteViewPageState extends State {

String url;

PhoteViewPageState(this.url);

@override

Widget build(BuildContext context) {

return new Scaffold(

appBar: new AppBar(

title: new Text('图片浏览'),

backgroundColor: Colors.green,

),

body: new Container(

color: Colors.white,

child: PhotoView(imageProvider: new CachedNetworkImageProvider(url),

backgroundDecoration: new BoxDecoration(color: Colors.white),

),

),

);

}

@override

void initState() {

super.initState();

}

@override

void dispose() {

super.dispose();

}

@override

void didUpdateWidget(PhoteViewPage oldWidget) {

super.didUpdateWidget(oldWidget);

}

@override

void didChangeDependencies() {

super.didChangeDependencies();

}

}

七、多图片浏览

使用TabbarView 与PhoteView 实现多图片的浏览

import 'package:flutter/material.dart';

import 'package:cached_network_image/cached_network_image.dart';

import 'package:photo_view/photo_view.dart';

class MutiPhotePage extends StatefulWidget {

List urls;

int postion;

MutiPhotePage(this.urls, this.postion);

@override

MutiPhotePageState createState() => new MutiPhotePageState(urls, postion);

}

class MutiPhotePageState extends State with SingleTickerProviderStateMixin{

List urls;

int postion;

TabController tabController;

MutiPhotePageState(this.urls, this.postion);

List getTabView() {

return urls.map((url) {

return new Container(

child: PhotoView(

imageProvider: new CachedNetworkImageProvider(url),

backgroundDecoration: new BoxDecoration(color: Colors.white),

),

);

}).toList(growable: true);

}

@override

void initState() {

super.initState();

this.tabController =

new TabController(length: urls.length, initialIndex: postion,vsync: this);

}

@override

void dispose() {

super.dispose();

}

@override

void didUpdateWidget(MutiPhotePage oldWidget) {

super.didUpdateWidget(oldWidget);

}

@override

void didChangeDependencies() {

super.didChangeDependencies();

}

@override

Widget build(BuildContext context) {

return new Scaffold(

appBar: new AppBar(

title: new Text("查看多张图片"),

backgroundColor: Colors.green,

),

body: new Container(

child: new TabBarView(

children: getTabView(),

controller: tabController,

),

),

);

}

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值