Dart (Programming Language) + Flutter (Mobile UI Framework) = Usable App
Course Flow
-
Basics of the Dart Language (Browser-based Editor)
-
Building Projects + Packages with Dart (Local Code Editor)
-
Building Apps with Dart + Flutter (Local Code Editor + Mobile Device Emulator)
Few Notes on Dart
-
Object-Oriented Language - (Most of our time is spent thinking about how to organize code in objects, or 'classes')
-
Statically Typed - (Variables contain data of a single 'type', like an integer or a string)
-
C-style Syntax - (Syntax of the language is very similar to C, C#, Javascript)
-
Multiple Runtime Environments - (Transpiled to Javascript to run in the browser. Runs in the 'Dart VM' to execute from a command line. Compiled to machine code to run on mobile devices)
- https://dartpad.dartlang.org/ - Browser based tool for playing around with Dart
void main()
{
var name = myName();
print('My name is $name');
}
String myName()
{
return 'Stephen';
}
var name = myName();
var - Declares a variable
name - Variable's name is 'name'
var name - Variable Declaration
myName(); - Runs the 'myName' function
= myName(); - Variable Initialization
String myName()
{
return 'Stephen';
}
String - Type of value that will be returned myName - Name of Function () - Argument List return 'Stephen'; - Function Body
Time
-
Program starts up
-
Dart finds and runs the 'main' function
-
Main function starts up the rest of our app
Types in Dart
-
Every value has a 'type'
-
Every variable has a type it can reference
-
Once a variable has a 'type' associated, the variables type cannot change
-
We don't always have to annotate types, Dart can guess for us
Your Computers Memory
name -> 'Stephen'
name - Variable that can reference type String 'Stephen' - Value with type String
TYPE ERROR EXAMPLE:
void main()
{
var name = myName();
name = 123;
print('My name is $name');
}
String myName()
{
return 'Stephen';
}
A value of type 'int' can't be assigned to a variable of type 'String'
name -> 'Stephen'
name - Variable that can reference type String 'Stephen' - Value with type String
TYPE INFERENCE EXAMPLE:
void main()
{
var name = myName();
print('My name is $name');
}
myName()
{
return 'Stephen';
}
Type | Example Value |
---|---|
String | 'hi', 'Hows it going?', 'Thats great' |
int | 0, -999, 876000 |
double | 0.0001, -999.814, 100.1 |
dynamic | 'Hi', -0.0004, 90 |
TYPE ERROR EXAMPLE:
void main()
{
var name = myName();
name.length;
print('My name is $name');
}
int myName()
{
return 123;
}
The getter 'length' isn't defined for the class 'int'
Why types at all?
-
Performance can be improved
-
Easier to work on large projects
-
Less of a need to write unit tests
-
Automatically find simple errors
void main()
{
var name = myName();
print('My name is ${name.length}');
}
myName()
{
return 'Stephen';
}
My name is Stephen.length
void main()
{
var name = myName();
print('My name is $name.length');
}
myName()
{
return 'Stephen';
}
My name is 7
- Object (Pieces of Data <- Methods)
Piece of Data - Information about our application hidden from other parts of the app
Method - Functions that govern access to data stored in the object
-
Class (Pieces of Data <- Methods) - Template of the Objects
-
Object/Instance ('red', 123 <- Methods)
Class (House Blueprints) -> Instances (Each Instance is a House)
Fields | |
---|---|
name | type |
firstName | string |
Methods |
---|
name |
printName |
class Person
{
String firstName;
printName()
{
print(firstName);
}
}
void main()
{
var person = new Person();
person.firstName = 'Stephen';
person.printName();
}
class Person
{
String firstName;
printName()
{
print(firstName);
}
}
void main()
{
var person = new Person('Stephen');
person.printName();
}
class Person
{
String firstName;
Person(this.firstName);
printName()
{
print(firstName);
}
}
Time
-
Call classes constructor function with arguments
-
Constructor function executed, does some initial setup
-
New instance of class returned
class Person
{
String firstName;
Person(this.firstName);
}
Person - Constructor function because it has the same name as the class
new Person('Stephen');
'Stephen' - First argument to constructor function
Deck of Cards
-
Ace of Diamonds
-
Two of Diamonds
-
Three of Diamonds
-
Four of Diamonds
-
Ace of Spades
Deck Program
-
Make a Deck - Create a new deck of playing cards
-
printCards - Print all the cards in this deck
-
shuffle - Shuffle the cards in this deck
-
cardsWithSuit - Find all the cards with a given suit
-
deal - Deal out some number of cards from this deck
-
removeCard - Remove a specific card from the deck
Dart Program Design Flow
Think about... | Then... | |
---|---|---|
What different types of 'things' exist in our app? | -> | Create a dart 'class' to represent each type of 'thing' |
What pieces of data would be tied to each 'thing'? | -> | Create a 'field' on each class to hold that piece of data |
How would we interact with each 'thing' and the data it contains? | -> | Add methods to represent each interaction |
How do different 'things' interact with each other? | -> | Write code outside of a class to get classes to interact |
Fields | |
---|---|
name | type |
Methods |
---|
name |
Fields | |
---|---|
name | type |
Methods |
---|
name |
class Deck
{
}
class Card
{
}
Fields | |
---|---|
name | type |
cards | List |
Methods |
---|
name |
Fields | |
---|---|
name | type |
suit | string |
rank | string |
Methods |
---|
name |
class Deck
{
List<Card> cards;
}
class Card
{
String suit;
String rank;
}
Fields | |
---|---|
name | type |
cards | List |
Methods |
---|
name |
printCards |
shuffle |
deal |
removeCard |
Fields | |
---|---|
name | type |
suit | string |
rank | string |
Methods |
---|
name |
??? |
class Deck
{
List<Card> cards;
Deck()
{
}
}
class Card
{
String suit;
String rank;
}
-
ranks = ['Ace', 'Two', 'Three', 'Four', ...]
-
suit = ['Hearts', 'Diamonds', ...]
For every suit in the suits list ...
-
For every rank in the ranks list ...
- Create a new card and add it to the 'cards' list
class Deck
{
List<Card> cards;
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
}
}
}
}
class Card
{
String suit;
String rank;
}
void main()
{
new Deck();
}
class Deck
{
List<Card> cards;
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
}
Uncaught exception: C.JSNull_methods.add$1 is not a function
List<Card> cards
List - Declares a field
cards - Fields name is 'cards'
List cards - Variable declaration
Your Computers Memory
cards -> ???
cards (Variable that can reference type List)
cards -> null
void main()
{
new Deck();
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
}
void main()
{
var deck = new Deck();
print(deck);
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
}
Instance of 'Deck'
print ( value )
value - Do you have a 'toString()' method? If so, run it!
void main()
{
var deck = new Deck();
print(deck);
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
toString()
{
return 'This is a deck!';
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
}
void main()
{
var deck = new Deck();
print(deck);
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
toString()
{
return cards.toString();
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
toString()
{
return '$rank of $suit';
}
}
-
Dart Documentation - https://api.dartlang.org/stable/2.0.0/index.html
-
List Class Docs - https://api.dartlang.org/stable/2.0.0/dart-core/List-class.html
-
Look for the method
shuffle
void main()
{
var deck = new Deck();
deck.shuffle();
print(deck);
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
toString()
{
return cards.toString();
}
shuffle()
{
cards.shuffle();
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
toString()
{
return '$rank of $suit';
}
}
Deck of Cards
-
Ace of Diamonds
-
Two of Diamonds
-
Three of Diamonds
-
Aces of Spades
-
Two of Spades
--------> cardsWithSuit('Spades') -------->
-
Ace of Spades
-
Two of Spades
void main()
{
var deck = new Deck();
deck.shuffle();
print(deck);
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
toString()
{
return cards.toString();
}
shuffle()
{
cards.shuffle();
}
cardsWithSuit(String suit)
{
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
toString()
{
return '$rank of $suit';
}
}
void main()
{
var deck = new Deck();
deck.shuffle();
print(deck.cardsWithSuit('Diamonds'));
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
toString()
{
return cards.toString();
}
shuffle()
{
cards.shuffle();
}
cardsWithSuit(String suit)
{
return cards.where((card)
{
return card.suit == suit;
});
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
toString()
{
return '$rank of $suit';
}
}
void main()
{
var deck = new Deck();
deck.shuffle();
print(deck.cardsWithSuit('Diamonds'));
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
toString()
{
return cards.toString();
}
shuffle()
{
cards.shuffle();
}
cardsWithSuit(String suit)
{
return cards.where((card) => card.suit == suit);
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
toString()
{
return '$rank of $suit';
}
}
-
List Class Docs - https://api.dartlang.org/stable/2.0.0/dart-core/List-class.html
-
Look for the method
sublist
Cards
- Card 0
- Card 1
- Card 2
- Card 3
- Card 4
- Card 5
Memory
List:
- 0 -> Card # 1
- 1 -> Card # 2
- 2 -> Card # 3
- 3 -> Card # 4
SubList:
- 0 -> Card # 1
- 1 -> Card # 2
void main()
{
var deck = new Deck();
print(deck);
print(deck.deal(5));
print(deck);
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
toString()
{
return cards.toString();
}
shuffle()
{
cards.shuffle();
}
cardsWithSuit(String suit)
{
return cards.where((card) => card.suit == suit);
}
deal(int handSize)
{
var hand = cards.sublist(0, handSize);
cards = cards.sublist(handSize);
return hand;
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
toString()
{
return '$rank of $suit';
}
}
-
https://api.dartlang.org/stable/2.0.0/dart-core/List-class.html
-
Method
removeWhere
void main()
{
var deck = new Deck();
deck.removeCard('Diamonds', 'Ace');
print(deck);
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var suit in suits)
{
for(var rank in ranks)
{
var card = new Card(rank, suit);
cards.add(card);
}
}
}
toString()
{
return cards.toString();
}
shuffle()
{
cards.shuffle();
}
cardsWithSuit(String suit)
{
return cards.where((card) => card.suit == suit);
}
deal(int handSize)
{
var hand = cards.sublist(0, handSize);
cards = cards.sublist(handSize);
return hand;
}
removeCars(String suit, String rank)
{
cards.removeWhere((card) => (card.suit == suit) && (card.rank == rank));
}
}
class Card
{
String rank;
String suit;
Card(this.rank, this.suit);
toString()
{
return '$rank of $suit';
}
}
void main()
{
var deck = new Deck();
deck.removeCard('Diamonds', 'Ace');
print(deck);
}
class Deck
{
List<Card> cards = [];
Deck()
{
var ranks = ['Ace', 'Two', 'Three', 'Four', 'Five'];
var suits = ['Diamonds', 'Hearts', 'Clubs', 'Spades'];
for(var mySuit in suits)
{
for(var rank in ranks)
{
var card = new Card(
suit: mySuit,
rank: rank
);
cards.add(card);
}
}
}
toString()
{
return cards.toString();
}
shuffle()
{
cards.shuffle();
}
cardsWithSuit(String suit)
{
return cards.where((card) => card.suit == suit);
}
deal(int handSize)
{
var hand = cards.sublist(0, handSize);
cards = cards.sublist(handSize);
return hand;
}
removeCars(String suit, String rank)
{
cards.removeWhere((card) => (card.suit == suit) && (card.rank == rank));
}
}
class Card
{
String rank;
String suit;
Card({this.rank, this.suit});
toString()
{
return '$rank of $suit';
}
}
flutter create pics
- Start New Android Studio Project -> Next -> Next -> Next -> Next
- AVD Manager -> Create Virtual Device
flutter emulators
flutter run
1. Download VS Code
In your browser, navigate to https://code.visualstudio.com/download and download the version of VS Code appropriate for your operating system.
2. Install VS Code
Once you've downloaded the installer, run it to start up the VS Code installer.
3. Start VS Code
4. Install the Flutter editor package
With VS Code open, find the menu bar at the top marked 'View' then click on 'Extensions'. This will open up a side bar tab used to install extensions. Search for a package called 'Flutter' and click the green 'install' button.
How do we make Flutter Apps?
-
We build widgets that control UI elements on the screen
-
We mix and match widgets to build the desired UI for the app we're making
-
Some widgets are provided by Flutter
-
Some are created by you and me
Example
-
Your Todos - (AppBar)
- All - (TabBar)
- Today - (TabBar)
- Tomorrow - (TabBar)
-
Todos - (BottomNavigationBar)
-
Contacts - (BottomNavigationBar)
-
Calls - (BottomNavigationBar)
-
+ - (FloatingActionButton)
Reference
General Idea
-
V1
- Let's See Images!
- +
-
V2
- Let's See Images!
- +
- Image Container (Image, Image Title)
-
V3
- Let's See Images!
- +
- Multiple Image Containers (Image, Image Title)
Go to the folder pics
where's our flutter project and run it:
flutter run
Open pics
folder on VSCode
pics > lib > main.dart
// I need to import a helper library
// from flutter to get content on the screen
// Define a 'main' function to run when our app starts
// Create a new text widget to show some text
// on the screen
// Take that widget and get it on the screen
Imports
-
Flutter Standard Library - animation, gestures, material, physics, rendering, scheduler
-
Our App - main.dart
-
Dart Standard Library - dart:io, dart:core, dart:async, dart:collection, dar:mirrors, dar:isolate
// I need to import a helper library
// from flutter to get content on the screen
import 'package:flutter/material.dart';
// Define a 'main' function to run when our app starts
// Create a new text widget to show some text
// on the screen
// Take that widget and get it on the screen
import 'package: flutter /material.dart'
- import - We are trying to import some code from somewhere else
- 'package: - We are importing code fromm a third party package, not a dart standard lib
- flutter - The name of the package we are importing
- /material.dart' - The file we are importing from that package
// I need to import a helper library
// from flutter to get content on the screen
import 'package:flutter/material.dart';
// Define a 'main' function to run when our app starts
void main()
{
// Create a new text widget to show some text
// on the screen
var app = MaterialApp(
home: Text('Hi there!'),
);
// Take that widget and get it on the screen
}
// I need to import a helper library
// from flutter to get content on the screen
import 'package:flutter/material.dart';
// Define a 'main' function to run when our app starts
void main()
{
// Create a new text widget to show some text
// on the screen
var app = MaterialApp(
home: Text('Hi there!'),
);
// Take that widget and get it on the screen
runApp(app);
}
- https://flutter.io/docs/reference/widgets/catalog
- https://docs.flutter.io/flutter/material/Scaffold-class.html
import 'package:flutter/material.dart';
void main()
{
var app = MaterialApp(
home: Scaffold(
appBar: AppBar(),
),
);
runApp(app);
}
import 'package:flutter/material.dart';
void main()
{
var app = MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text('Lets see some images!'),
),
),
);
runApp(app);
}