Skip to content

Instantly share code, notes, and snippets.

@andantonyan
Created February 11, 2022 17:19
Show Gist options
  • Save andantonyan/f8255dcac0f38a84e10c39616245003e to your computer and use it in GitHub Desktop.
Save andantonyan/f8255dcac0f38a84e10c39616245003e to your computer and use it in GitHub Desktop.
Render conditional section using factory and COR patterns
import 'package:flutter/material.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: const MyHomePage(),
);
}
}
class MyHomePage extends StatefulWidget {
const MyHomePage({Key? key}) : super(key: key);
@override
State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
String _name = 'scale';
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Test'),
),
body: Center(
child: Builder(
builder: (context) {
QuestionSection? section;
try {
section = QuestionSection.create(_name);
} catch (err) {
print(err);
}
return section ?? Container();
},
),
),
floatingActionButton: FloatingActionButton(
onPressed: () => setState(() => _name = _name == 'scale' ? 'choice' : 'scale'),
backgroundColor: Colors.blue,
child: const Icon(Icons.change_circle),
),
);
}
}
abstract class QuestionSection implements Widget {
static final QuestionSectionAbstractResolver _resolvers = ScaleQuestionResolver()..setNext(ChoiceQuestionResolver());
factory QuestionSection.create(String name) {
var section = _resolvers.resolve(name);
if (section != null) {
return section;
} else {
throw Exception('Unable to create instance for name: $name');
}
}
final String name;
const QuestionSection(this.name);
}
class ScaleQuestionSection extends StatelessWidget implements QuestionSection {
@override
final String name;
const ScaleQuestionSection({
Key? key,
required this.name,
}) : super(key: key);
@override
Widget build(BuildContext context) {
return Container(
color: Colors.pinkAccent,
height: 300,
width: 300,
child: Text(
'Name $name',
style: const TextStyle(color: Colors.white),
),
);
}
}
class ChoiceQuestionSection extends StatelessWidget implements QuestionSection {
@override
final String name;
@override
const ChoiceQuestionSection({Key? key, required this.name}) : super(key: key);
@override
Widget build(BuildContext context) {
return Container(
color: Colors.blueGrey,
height: 300,
width: 300,
child: Text(
'Name $name',
style: const TextStyle(color: Colors.white),
),
);
}
}
abstract class QuestionSectionAbstractResolver {
QuestionSectionAbstractResolver? _nextResolver;
QuestionSectionAbstractResolver setNext(QuestionSectionAbstractResolver resolver) {
_nextResolver = resolver;
return resolver;
}
QuestionSection? resolve(String name) {
if (_nextResolver != null) {
return _nextResolver!.resolve(name);
}
return null;
}
}
class ScaleQuestionResolver extends QuestionSectionAbstractResolver {
ScaleQuestionResolver();
@override
QuestionSection? resolve(String name) {
if (name == 'scale') {
return ScaleQuestionSection(name: name);
}
return super.resolve(name);
}
}
class ChoiceQuestionResolver extends QuestionSectionAbstractResolver {
ChoiceQuestionResolver();
@override
QuestionSection? resolve(String name) {
if (name == 'choice') {
return ChoiceQuestionSection(name: name);
}
return super.resolve(name);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment