Implement Flutter’s BLoC architecture

shogo.yamada
2 min readJan 8, 2019

--

Implement Flutter’s BLoC architecture

I will show you how to implement the famous BLoC architecture by Flutter.

Constitution

The composition is like this.

I will do the package composition like this.

Implementation

Let’s paste the source code.

Prepare and implement UIScreen.

  • main.dart
import 'package:flutter/material.dart';
import 'package:flutter_app_bloc_sample_app/src/app.dart';

void main() => runApp(App());
  • app.dart
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_app_bloc_sample_app/src/ui/scenery_list.dart';

class App extends StatelessWidget {

@override
Widget build(BuildContext context) {
return MaterialApp(
theme: ThemeData.dark(),
home: Scaffold(
body: SceneryList(),
),
);
}
}

UI Screen

  • ui/scenery_list.dart
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_app_bloc_sample_app/src/blocs/scenery_bloc.dart';
import 'package:flutter_app_bloc_sample_app/src/models/image_model.dart';

class SceneryList extends StatelessWidget {
final _bloc = SceneryBloc();

@override
Widget build(BuildContext context) {
_bloc.fetchAllScenery();
return Scaffold(
appBar: AppBar(
title : Text ( "Landscape image list" ),
),
body: StreamBuilder(
stream: _bloc.allScenery,
builder: (_, snapshot) {
if (snapshot.hasData) {
return _buildList(snapshot);
} else if (snapshot.hasError) {

return Text ( "An error occurred" + snapshot.error.toString ());
}

return Center(
child: CircularProgressIndicator(),
);
}),
);
}

Widget _buildList(AsyncSnapshot<List<ImageModel>> snapshot) {
return GridView.builder(
gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount : 2 ),
itemBuilder: (_, index) {
ImageModel model = snapshot.data[index];
return Image.network(model.imageUrl);
},
itemCount: snapshot.data.length,
);
}
}

It is the part of BLOC.

  • scenery_bloc.dart
import 'package:rxdart/rxdart.dart';
import 'package:flutter_app_bloc_sample_app/src/models/image_model.dart';
import 'package:flutter_app_bloc_sample_app/src/resources/repository.dart';

class SceneryBloc {
final _repository = Repository();
final _sceneryFetcher = PublishSubject<List<ImageModel>>();

Observable<List<ImageModel>> get allScenery => _sceneryFetcher.stream;

fetchAllScenery() async {
List<ImageModel> imageModelList = await _repository.fetchAllProvider();
_sceneryFetcher.sink.add(imageModelList);
}

has () {
_sceneryFetcher.close();
}
}

Next, Repository

import 'package:flutter_app_bloc_sample_app/src/models/image_model.dart';

import 'scenery_image_provider.dart';

class Repository {
final provider = new SceneryImageProvider();

Future<List<ImageModel>> fetchAllProvider() => provider.fetchImageList();
}

Next, Network Provider

import 'package:flutter_app_bloc_sample_app/src/models/image_model.dart';
import 'package:http/http.dart' show Client;
import 'dart:convert';


class SceneryImageProvider {
Client Client = Customer ();

Future < List < ImageModel >> fetchImageList () async {
/ / I prepared the Json. So please use it.
final response = await client. get (
"https://firebasestorage.googleapis.com/v0/b/blog-1a47d.appspot.com/o/json%2Fdata.json?alt=media&token=e67da5e7-b8d4-4000-9dc3 -394e6a5d1549 " );

print(response.body);
if (response.statusCode == 200) {
// success
List<dynamic> jsonArray = JsonDecoder().convert(response.body);
return jsonArray.map((i) => ImageModel(i)).toList();
} else {
// fail
throw Exception('Failed to load post');
}
}
}

This is completed.

The actual moving image will be below.

I put the source code in this repository.

--

--

shogo.yamada
shogo.yamada

Written by shogo.yamada

普段はエンジニアやってます👨‍💻 自分の資産運用の記録として書いてり、プライベートなことを書いていきます。

No responses yet