Prototyping beautiful designs with Flutter

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
[MUSIC PLAYING] BRIAN JAMES: Hi, I'm Brian, a User Experience Engineer on the Flutter UX team. I combined my background in design and code to help build Flutter and explore its creative possibilities. LEIGHA JARRETT: And I'm Leigha, a Product Manager for Flutter focusing on design and the Apple ecosystem. Now, you probably already knew about Flutter's speed and productivity. But today, we're going to talk about creativity and why Flutter is such a great choice for bringing your unique, ambitious designs to life. To show you what we mean, we'll take on the role of creative coders, working on a fictional font-themed puzzle app with complex animations and custom special effects. Now, this won't be a tutorial, but we'll show you examples of how Flutter's easy-to-use components and its powerful graphics features can be combined to create a unique design. We'll start with simple widgets and custom styling and build up to complex topics like animations, custom graphics drawings, platform adaptivity, and even variable fonts and shader support. So whether you're a Flutter newcomer or a seasoned pro, we think you'll find some new ideas to explore. Let's start by looking at our design mockup-- in this case, a Figma prototype for our new game. The concept is that the player just got hired at a font company, and their first job is to publish a new font file. But when they click the OK button too hard, it scrambled the font. So now, they're seeing all these letters are kind of wonky, and their job is to put them back together by solving the puzzles. OK, sounds fun. So now, let's get started writing some code. BRIAN JAMES: Let's start simple. The first screen is pretty straightforward. We've got a couple of text blocks with different fonts and a button. In Flutter, everything is made of composable, reusable UI elements called widgets, and that makes building app screens really easy. So in our case, we might want a few widgets for the text blocks and one more widget for the button. For those of you just getting into Flutter, be sure to check out the amazing documentation that the Flutter team has available at docs.flutter.dev, specifically, the widget catalog. Right now, we want the Text category. And here, we have the Text widget. There are even examples of how to use it. LEIGHA JARRETT: Awesome. I'll go ahead and add this into our app code. First, I'll create a new widget to hold the contents of our first page. And inside this widget, I'll add the Text widget that says our little welcome bit. I'll also create a few other text widgets to hold our alphabet strings. Oh, and one other point for new Flutter devs-- widgets aren't just for components like texts or buttons. They're also used to control the layout. Basically, everything is a widget. So watch how I can use a Column layout widget to stack the different Text widgets on top of each other. And I can use the Padding widget to specify the amount of space surrounding the Text blocks. Next, we need to create our button. So Flutter lets you easily create different styles of buttons to match the design of your app. These ready-made buttons look great out of the box, but if the style isn't quite what you had in mind, you can use it as a starting point and customize its look. You're probably already familiar with Material Design, the design system used here at Google, and Flutter has several button options that fit into that system. In our case, let's use an ElevatedButton. We can add ElevatedButton as a child of our Column widget. And now we can see it in our app. I think we're off to a good start, but the font and colors, they don't really match what we originally had in mind. To control app-wide settings like different textiles, color schemes, or styles for individual classes, we can create a theme. An app theme is kind of like a style sheet. So in Flutter, you create a theme by using ThemeData. And to propagate the settings to all the widgets within the app, we can use ThemeData as an input to the MaterialApp class. BRIAN JAMES: Before we specify our fonts, we'll need to bundle the font files into our app. I can just drag and drop them into the project folder and then specify them in the assets section of the pubspec file, which contains metadata about the Flutter project. Or I can use the Flutter google_fonts package which lets me bypass this step. It downloads whatever Google font I want on the fly, which is especially useful to try out several fonts. LEIGHA JARRETT: Great, so now we can use those fonts in our ThemeData by creating different text styles. Here, we can use a TextTheme, and within it, we'll create different text styles that correspond with the different font families or sizes used in our app. To specify what style we want our Text widget to use, we can refer to it in the style parameter. Our text is looking good, so now on to the button. We can control the color scheme for our entire app, or we can use theme classes that are specific to the widget classes that we're using. In this case, we'll use the ElevatedButton theme and specify the background color. And now we can see the screen is looking just like our designs. BRIAN JAMES: These customized themes give us a lot of design options, but it doesn't stop there. With Flutter, we can easily make fully custom UI components that don't look like conventional buttons or switches or sliders. Just to scratch the surface of the possibilities, let's say we wanted to make something a little quirky, like a button with two sharp corners and two rounded corners. It's not as hard as you might think. Let's start with a Container widget, which is a very generic widget that just gives us a box on the screen. And we can control its appearance with a BoxDecoration. LEIGHA JARRETT: Now, I can use that in a brand new widget class called MyCoolButton, which will return a container with a BoxDecoration. Within BoxDecoration, we can change the BorderRadius for two of the corners to make them curved. Plus, we can use the backgroundColor that we defined in our button theme earlier. So let's move on to the next page of the app, the settings. Now I know a settings page doesn't sound very exciting, but stay with us, because we're about to show you a great trick. We'll make a simple settings page to turn the sound on or off. And for this, I'll just go ahead and use the Switch widget from the material library that we tested before. But now that I'm taking a closer look, this looks great for Android devices, but native switches on iOS look a bit different. Thankfully, Flutter also has the Cupertino library, which includes a set of widgets that use Apple's Human Interface Guidelines. Here, we can see this looks more familiar to iOS users. And even better, I can use the .adaptive name constructor to create a Switch widget that will automatically alternate between Material and Cupertino depending on what platform the game is played on. So Flutter can actually sense which operating system the app is running on and change the designs accordingly. BRIAN JAMES: Flutter also does a bunch of platform adaptations automatically behind the scenes, really detailed things like scrolling speed, what happens when you scroll to the bottom of a page, and haptic feedback to help your apps feel natural, whatever platform they're used on. LEIGHA JARRETT: That's so important to make cross-platform apps easy to use for the consumer. Anyways, let's keep chugging along. So before we get to the game itself, let's try and tackle the page that a user sees when they finish the puzzle. First, we have a Congratulations textbox. And then we have a line chart showing the user how many moves it took to solve the puzzle each time they played. It's kind of tracking their score over time. We already know about the Text widget, so let's focus on that line chart. We want to be able to draw a line between different points, and the placement of those points will depend on the number of games that the user has played and how many times it took for them to win. So far, we've seen how to make custom boxes and box shapes, but I don't think that's going to work here. If we want to draw custom shapes, curves, or lines, we can use the CustomPaint widget. It works a lot like a pen tool in a digital illustration app, where we draw a path between various points. But since we're creating these points programmatically, then we can respond to different inputs from our app, like the player stats that we'll be using here. First, we'll use the CustomPaint widget, and then we'll need to create a custom class to use as the painter. Our LineChartPainter will specify the stroke color and width that we'll use. And in our case, we'll create two paints, one for the axis and one for the data on the chart. We'll also create two paths. For the axis path, I can just draw a line vertically to the canvas height and horizontally to the canvas width. Now, for the data, I can loop through each point and draw a line to that coordinate. Then we simply feed in the paint and path object to draw the path on the canvas. And even though we're just drawing a few straight lines for this example, CustomPaint lets you draw really complex shapes with combinations of lines, bezier curves, and multiple closed or open paths. It gives you so many possibilities, and if you're looking for inspiration, check out gskinner's vignettes. BRIAN JAMES: At this point, we've seen some standard widgets like Text and Container, some widgets that follow established design systems like Material Design and Apple's Human Interface Guidelines, and we've built totally custom widgets to match our own designs. Now let's bring those widgets to life with some animations. Motion design is one of the most interesting and expressive types of design. It's also a great bridge between classic visual design and interface or interaction design. Flutter gives you a range of tools for animations, so let's start with the simplest ones. There's a collection of animated widgets ready for motion out of the box with almost no extra code. These are called implicit animations, and they're a convenient way to implement simple motion designs in your app. Just like regular widgets, we have a variety of parameters we can use to customize how a widget looks, like the color of this animated container, which is set to red. With implicitly animated widgets like AnimatedContainer, when a parameter like this gets changed, the widget automatically animates from the old setting to the new one. Let's apply this to the Congratulations text on our end screen. We'll make the text animate up in size and get darker in color just for fun. Fortunately, there's one of these implicitly animated widgets for just such an occasion, AnimatedDefaultTextStyle. I've wrapped my Text widget in the AnimatedDefaultTextStyle and use the named parameters to control the visuals, like duration, which sets the animation's speed, and fontSize, and color to set the size and color, using two variables. Higher up, we've set those variables to our start settings, small size and transparent color. Animations can be kicked off by basically any event you want, like tapping a button or new data coming in. In this case, let's use a timer, like this. It has a half-second delay, and then it changes the size and color variables that we set up before. So the text will hold for just a moment on the start settings, then animate to this new size and color, like this. We can even customize the animation timing or curve. The default curve is called linear, and it goes straight from A to B, like we just saw. But we can also manually set a curve like this, with a bunch of great options like easeOut for a subtle slowdown at the end, or even bounceOut. And just like that, we have an animation for our end screen. LEIGHA JARRETT: Now, we're not expecting you to memorize all of these, but do remember to check out Flutter's great reference docs and the official YouTube channel with bite-sized tutorials like "Widget of the Week," as well as longer podcast-style content. If you're new to Flutter, we highly recommend the "Learning to Fly" series. So using the ready-made implicitly animated widgets is really convenient and powerful, but what if there isn't an animated widget for what we want to do or we have a more complicated animation in mind? BRIAN JAMES: For example, let's say we want to animate the line chart we made earlier so that the line draws across the screen rather than just popping on. That's very customized, so we'll need to create our own animation from scratch. Flutter calls these explicit animations. Explicit animations use animation controllers, which, as you've probably guessed, let us control the animations. There are a few ways we can use animation controllers. One of the most common involves tween objects. That's short for "in between," like animating between a start and an endpoint. This next part will get a bit complex, so we're going to leave out some details and just focus on the most crucial parts of the code. Having set up the AnimationController, we'll create a tween sequence to animate from one point on the graph to another. These points are called offsets in the code. Next, we add a listener. For every frame of the animation, the listener updates the dx and dy variables, which control how much of the graph we draw in each frame. Those variables get plugged into the custom painter we set up before like this. And there we have it. Our chart draws itself with a custom animation we created. LEIGHA JARRETT: So far, we've been building up the intro and outro pages of our game. Now let's start getting into the game itself. We've already dabbled with some subtle animations, but let's go big this time. What if we take the letters surrounding the puzzle pieces and distort them? This kind of effect is made possible by variable fonts. They give designers deep control over text styling. So with variable fonts, we can control not just the size and the boldness, but any other settings that the font creator allows us to. This could include things like the width of the letters, the relative size of different parts, all kinds of really detailed settings. BRIAN JAMES: Flutter lets you use variable fonts with the TextStyle class, which we talked about earlier. We access individual variable font parameters with the FontVariation class. And you can add and combine as many of the font variations as the font file itself supports by plugging them into the TextStyle's fontVariations field. Variable fonts can be great for practical things like increasing legibility, but they can also provide a bit of visual flair, especially when they're combined with animation. I think animating between extreme settings will really add to the glitchy concept of the game's story, so let's give it a try. Let's say we want to animate a variable font from a very lightweight, like 100, to a very bold weight, like 1,000. This is a custom explicit animation, so we'll use an AnimationController and a Tween again, which we're already familiar with. You can see we're animating the Tween from 100 to 1,000. Remember that we've named this Tween variable "animation" because we'll use it again. One new point in the code is the curved animation we've set up, which is one way to attach a timing curve like bounce or ease to an explicit animation. Here, we're using ease in and out. We connect that Tween as animation.value with the FontVariation for weight, like this. And remember that the FontVariation lives inside a TextStyle, like this. And if we do this on a bunch of letters at different speeds, we get this, exactly what we wanted. And we're not limited to animating the font's boldness, like we see on the left. In the middle, we see our variable font changing widths and even things like ascenders and descenders, how high and how low the tops and the bottoms of the letters extend. This was kind of a weird idea, but I think it's working nicely. LEIGHA JARRETT: The variable font animations are definitely creating a cool distorted effect, but let's push it even further. I think we could get a really glitchy, eye-catching feel with some custom shaders. Shaders are a pretty advanced topic, but if you want to get really into graphics programming, Flutter lets you create custom fragment shaders. Shaders are programs written in a specialized language separate from Flutter and Dart. They run directly on your computer's GPU, or Graphics Processing Unit, and they can create all kinds of visual effects. Flutter lets you code your own shaders and plug them into your app, so you can apply the effect to one widget or the entire screen. And because shaders run on the GPU, they take work off of the CPU, which helps you keep your app running at a high frame rate. BRIAN JAMES: We don't have time for a full shader tutorial today, and honestly, I'm not a shader expert by any means. But just to give a quick idea, this code snippet, written in GL Shader Language, will stretch the pixels of whatever it's applied to and create a wavy effect. And we can use regular animation controllers to make it move. Like before, we're just showing key parts of the code. But here, we're connecting an animation value into the fragmentShader object we just coded with GLSL, and we're using it in a custom painter. That's one way to apply this shader and make the effect shift over time, creating an animation. And there it goes. The shader effect is now animating, and we're controlling the animation through regular Flutter code. Again, shaders are a fairly advanced topic, but if you're up for a challenge, try experimenting with them in your next app. LEIGHA JARRETT: So we covered a lot of ground today, and don't worry if you didn't catch everything. Our main goal was to give you a few ideas to explore as you make your own amazing designs in Flutter. If you're new to Flutter and not sure what to do next, you might like to start with a no-installation web-based experience at DartPad.dev, where you can find sample apps to tinker with or even write your own simple app from scratch. Thanks for watching, and we can't wait to see what you create next. [MUSIC PLAYING]
Info
Channel: Flutter
Views: 42,164
Rating: undefined out of 5
Keywords: flutter forward, flutter forward 2023, flutter latest, flutter updates, what's new in flutter, how to use flutter, introduction to flutter, intro to flutter, flutter tutorial, flutter developer, flutter developers, google developer, google developers, google, flutter, dart, dash
Id: sA5MRFFUuOU
Channel Id: undefined
Length: 20min 37sec (1237 seconds)
Published: Wed Jan 25 2023
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.