Modular and customizable Material Design UI components for iOS

Overview

Material Components for iOS

Code coverage

Material Components for iOS (MDC-iOS) helps developers execute Material Design. Developed by a core team of engineers and UX designers at Google, these components enable a reliable development workflow to build beautiful and functional iOS apps. Learn more about how Material Components for iOS supports design and usability best practices across platforms in the Material Design Platform Adaptation guidelines.

Material Components for iOS are written in Objective-C and support Swift and Interface Builder.

Useful Links

Trying out Material Components

CocoaPods is the easiest way to get started (if you're new to CocoaPods, check out their getting started documentation.)

To install CocoaPods, run the following commands:

sudo gem install cocoapods

Our catalog showcases Material Components. You can use the pod try command from anywhere on your machine to try the components, even if you haven't checked out the repo yet:

pod try MaterialComponents

In case you have already checked out the repo, run the following command:

pod install --project-directory=catalog/

The component implementations can be found in Xcode within Pods > Development Pods > MaterialComponents.

Requirements

  • Xcode 10 or higher
  • Minimum iOS deployment target of 10.0 or higher
  • CocoaPods 1.5 or higher

Attributions

Material Components for iOS uses Material Design icons, copyright Google Inc. and licensed under CC BY 4.0.

Several components use MDFTextAccessibility, copyright Google Inc. and licensed under Apache 2.0 without a NOTICE file.

MDCCatalog uses the Roboto font, copyright 2011 Google Inc. and licensed under Apache 2.0 without a NOTICE file.

Comments
  • [Typography] Dynamic Type 2.0

    [Typography] Dynamic Type 2.0

    Next iteration of our Dynamic Type.

    Mimics Apple's new APIs. (UIFontMetrics) Adds MDCFontScalar to attach curves. Adds UIFont category to expose fontScaledForCategory methods. Adds new MDCTypographyScheme with scalable fonts.

    [Typography] cla: yes [NavigationBar] [Dialogs] [schemes] 
    opened by ianegordon 43
  • [Tabs] Add semanticContentAttribute support to MDCTabBar for RTL.

    [Tabs] Add semanticContentAttribute support to MDCTabBar for RTL.

    The collection view layout used internally to MDCItemBar has support for RTL, but it checks the effectiveLayoutDirection which is inferred from the semanticContentAttribute.

    This change updates MDCTabBar and MDCItemBar to forward changes of the semanticContentAttribute down to the collection view such that it lays itself out for RTL.

    NOTE: This behavior will not work on iOS 8 because it relies on semanticContentAttribute which was introduced in iOS 9.

    English pseudo language: https://i.imgur.com/ID7ex1o.png Hebrew: https://i.imgur.com/wwK3ztK.png

    Closes #5578

    cla: yes [Tabs] 
    opened by mrhappyasthma 43
  • React to Swift Package Manager - Internal issue: b/135017130

    React to Swift Package Manager - Internal issue: b/135017130

    This was filed as an internal issue. If you are a Googler, please visit b/135017130 for more details.


    Internal data

    • Associated internal bug: b/135017130
    • Blocked by: https://github.com/material-components/material-components-ios/issues/8433
    type:Feature request 
    opened by material-mirror 40
  • [BottomSheet] Disable pan gesture on UIControl

    [BottomSheet] Disable pan gesture on UIControl

    This change prevents touches to UIControl from being recognized by the bottomsheet's swipe gesture. This way a user doesn't accidentally starts dismissing the sheet while they are trying to interact with a control on the sheet.

    cla: yes [BottomSheet] PR:merge-when-approved 
    opened by linksmt 35
  • [Tabs] Internal fixes to account for the Safe Area insets.

    [Tabs] Internal fixes to account for the Safe Area insets.

    ~~Consists of two things: sizeThatFits takes into account any bottom safe area inset the tab bar might have, and~~ a few fixes to the collection view itself to make sure our content is laid out correctly.

    Closes #2012

    cla: yes [Tabs] iOS:11 device:iPhone X 
    opened by chuga 32
  • Make pod install work on Cocoapods 1.6.0.beta.2

    Make pod install work on Cocoapods 1.6.0.beta.2

    Original PR description:

    On Cocoapods version 1.6.0 beta 2 we get an error on pod install because certain test targets don't have any sources to compile. This PR adds some skeleton unit test source files to get that working. Is everyone okay with these (for now) basically empty files?

    Closes #5825

    FInal PR description:

    The original aim of this PR was to get the project working with the Cocoapods 1.6 beta.

    I initially didn't know where to begin getting it to work, so I used pod lib lint to get answers. pod lib lint had issues with the following things:

    1. test_specs not having any sources to compile. This was due to our pattern of putting unit test test_specs inside of parent test_specs that didn't have anything else.

    To address this I did two things. First, I moved away from the nested test_spec pattern. Now, instead of "Subspec/tests/unit_tests" it's "Subspec/UnitTests". This is more in line with the style Cocoapods uses here. Secondly, I added some dummy files for things like UIMetrics and MaterialMath.

    1. Importing headers across modules without using framework style imports.

    I added framework style imports. This required some additional rewrite rules in the kokoro script.

    1. Dependencies across subspecs being implicit.

    I made them explicit by adding dependency statements to the podspecs where needed.

    pod lib lint didn't take issue with this, but I also saw that MaterialComponents was depending on MaterialComponentsBeta in various places. For example, all the theming extensions were in beta, but the tests for them weren't. I moved the tests to test_specs within the beta extensions. This required some directory structure changes. These changes then required some BUILD file changes. Making BUILD file changes made me realize that some swift unit tests weren't being accounted for by bazel. I took care of this too.

    This PR also fixes some swift debugging stuff--"po" statements that weren't working before now do. I didn't rigorously verify this, but I also think this PR will lead to faster clean build times? It kinda seemed like it was while I was working on it.

    cla: yes [Buttons] [ButtonBar] [Dialogs] [ShadowElevations] [Chips] [Cards] [schemes] [private] [ActionSheet] [Catalog] 
    opened by andrewoverton 31
  • [FlexibleHeader] Add behavior for enabling contextual safe area insets

    [FlexibleHeader] Add behavior for enabling contextual safe area insets

    This is the first part of a two-part change that addresses the behavior outlined in https://github.com/material-components/material-components-ios/issues/4104. The second part will expose a similar behavior in the AppBar component.


    This PR introduces a new top safe area inset behavior to the flexible header view, gated behind the runtime flag inferTopSafeAreaInsetFromViewController.

    When this behavior is enabled, the flexible header will no longer attempt to infer the top safe area inset from the device's insets using MDCDeviceTopSafeAreaInset. Instead, it will infer the top safe area inset from the view controller ancestry of the flexible header view controller.

    This new behavior addresses a number of issues related to safe area insets, namely:

    • https://github.com/material-components/material-components-ios/issues/4104 (incorrect insets when shown in a popover or modal dialog on iPad).
    • Flexible headers can now be used in app extensions.
    • The flexible header now properly reacts to status bar visibility changes.

    New feature: top safe area guide

    This change introduces a new layout guide that can be used to position content within the flexible header view while respecting the top safe area insets. The topSafeAreaGuide API is available on the MDCHeaderView instance of the flexible header view controller and supports iOS 8 and up. An example of its usage to align a view to the bottom of the flexible header's top safe area guide:

    [NSLayoutConstraint constraintWithItem:self.titleLabel
                                      attribute:NSLayoutAttributeTop
                                      relatedBy:NSLayoutRelationEqual
                                         toItem:self.fhvc.headerView.topSafeAreaGuide
                                      attribute:NSLayoutAttributeBottom
                                     multiplier:1.0
                                       constant:0]
    

    The new layout guide works whether inferTopSafeAreaInsetFromViewController is enabled or disabled.

    Additional information

    If using MDCFlexibleHeaderContainerViewController, this new behavior is now enabled by default.

    The new behavior (and all of the other "new" behaviors) have been enabled on every FlexibleHeader example.

    Results

    A screenshot of the result of this API once enabled on the App Bar:

    simulator screen shot - ipad air - 2018-07-20 at 00 32 36

    Architecture

    This change builds off of the foundation introduced in 80fd217f766e0f5be6a3bc6bef5923f231721f9d. As part of that change, we made it possible to modify a given view controller's top layout guide such that it equalled the top safe area insets + the flexible header height. Unfortunately, that change was still limited by the fact that the flexible header always assumed that it was placed as a full-screen view.

    With the new inferTopSafeAreaInsetFromViewController behavior, we are able to extract the top safe area inset from our view controller ancestry instead. We can then combine this extracted value with our flexible header's height before ultimately writing that to the target top layout guide. This flow is roughly shown in the following diagram:

    fhv

    In order to implement this flow we needed to implement two things:

    1. A mechanism by which we could infer the root-most ancestral view controller from which we could extract safe area insets.
    2. A mechanism by which we could be notified every time that root view controller's safe area insets changed.

    The first mechanism is implemented by fhv_inferTopSafeAreaSourceViewController as a simple ancestral traversal. We walk up the view controller tree from the flexible header's parent until we run out of ancestors. There is some nuance to this algorithm, in that we need to ensure that our ancestor isn't our topLayoutGuideViewController or we risk creating an infinite loop. If we encounter such a situation we attempt to break the loop by walking up the topLayoutGuideViewController's ancestry instead, but at this point it's very likely we won't have a viable ancestor and we'll throw an assertion if/when we can't find a viable ancester.

    With an ancestor in hand, we then determine whether to KVO observe topLayoutGuide or safeAreaInsets based on whether we're running pre-iOS 11 or iOS 11+, respectively.

    KVO then informs us of any changes to the top safe area insets, which we can then propagate through the flexible header view and eventually on to the top layout guide (if topLayoutGuideAdjustmentEnabled is also enabled).

    cla: yes [FlexibleHeader] app:Catalog 
    opened by jverkoey 31
  • [NavigationDrawer] Move off of MDCDeviceTopSafeAreaInset.

    [NavigationDrawer] Move off of MDCDeviceTopSafeAreaInset.

    Resolves #4900, which was closed due to inactivity, but is still a relevant issue.

    We're currently running into an issue where, because view.safeArea.topInset is never used for non-notched devices, extra height is always added to our drawer headers on presentation to take account for the hard-coded status bar height of 20, even when displayed in fullscreen landscape mode where this does not apply.

    This is resolved by universally using the safeArea insets, rather than relying on MDCDeviceTopSafeAreaInset. This is done in favor of changing the behavior of MDCDeviceTopSafeAreaInset itself, as it is less clear to me what unintended effects that may have in other components.

    For devices running on iOS prior to 11.0, this change is a no-op, as the changes in MDCBottomDrawerViewController and MDCBottomDrawerContainerViewController will just use the hardcoded value of 20 that is always returned by MDCDeviceTopSafeAreaInset in a pre-"iOS 11" context.

    I have also removed usage of addedContentHeightThreshold as this was just a passthrough for accessing the top area inset and have consolidated to use one shared getter topSafeAreaInset throughout the MDCBottomDrawerContainerViewController.

    cla: yes [private] [NavigationDrawer] 
    opened by jakerockland 30
  • [Typography] Add new typography scheme with scalable fonts

    [Typography] Add new typography scheme with scalable fonts

    Adds a new scheme that vends fonts with an associated scaling curve.

    This is a BREAKING CHANGE due to a new, required property in the MDCTypographyScheming protocol. To easily migrate, clients can add the following method to their custom implementations of MDCTypographyScheming.

    - (BOOL)mdc_adjustsFontForContentSizeCategory {
      return NO;
    }
    
    [Typography] cla: yes [schemes] PR:merge-when-approved 
    opened by ianegordon 29
  • Snapshot Testing Proof of Concept

    Snapshot Testing Proof of Concept

    The problem

    We currently do not have UI tests on a component level. Integrating snapshot tests would allow us to have peace of mind with each PR that it isn't going to introduce any changes to the UI unless its intended to.

    The solution

    • Integrate ios-snapshot-test-case pod to handle generating and diffing images of components.
    • Integrate git-lfs to handle storage of the goldens.

    This PR creates one test to showcase the ability to do snapshot tests. Upon merging this PR, you must install git-lfs in order to properly have the images pulled down. The 3 steps to do this:

    1. brew install git-lfs
    2. git lfs install
    3. git lfs pull

    Additionally, the golden is generated using an iOS 11 simulator at 2x scale so that the kokoro jobs are happy.

    Related bugs

    Closes #5740

    cla: yes [Snackbar] [Cards] [Catalog] 
    opened by rami-a 28
  • [MDCSnackbarManager] Cannot write XCUITestCase / Element missing from tree hierarchy

    [MDCSnackbarManager] Cannot write XCUITestCase / Element missing from tree hierarchy

    I am working with XCUITestCase. When I display the snackBar, it's impossible to tapElement or to see any element from the SnackBar with the accessibility I checked inside the Accessibility Inspector and the whole SnackBar component is invisible from the tree hierarchy.

    Reproduction steps

    Steps to reproduce the behavior:

    • Create a snackBar
    • Open Accessibility Inspector
    • Try to see the SnackBar in the tree hierarchy
     func createSnackBar() {
            mdcSnackbarManager = MDCSnackbarManager()
            
            let action = MDCSnackbarMessageAction()
            action.title = "BURN"
            action.accessibilityLabel = "Action_accessibility_Label"
            action.accessibilityIdentifier = "Action_accessibility_Identifier"
            action.accessibilityHint = "Action_accessibility_Hint"
            action.handler = {
                
            }
            
            let message = MDCSnackbarMessage(text: "Popup from Hell")
            message.accessibilityLabel = "Action_accessibility_label"
            message.accessibilityHint = "Action_accessibility_hint"
            message.action = action
            
            mdcSnackbarManager?.show(message)
        }
    

    Expected behavior

    I would like to be able to fetch the elements (at least the action to dismiss view) with the specific identifier I setted to be able to tap on this Element with XCUITest.

    Actual behavior

    It looks like Snackbar component is invisible from the Accessibility context.

    I check with the XCUITestCase using in the console po app in my real project, but the snackbar doesn't appear.

    Screenshot 2022-11-08 at 18 31 35

    I tried the same with the accessibility Inspector, but same result.

    Here a small video: https://user-images.githubusercontent.com/8981703/200644811-205d00d5-e2d4-4e9b-abbf-0a854219bc23.mov

    Platform (please complete the following information)

    • Device: iPhone 14
    • OS: iOS 16.0

    Here the sample to check by yourself: SnackBarTest.zip

    opened by paul-lavoine 0
  • Implementing deprecated class

    Implementing deprecated class

    Hi, as I am updating project along with the new apple releases. But as this library hasn't been updated since 2021. So it's throwing a lot of deprecated warnings. I request an update to take care of the warning "Implementing deprecated class". My project is using OBJ-C Screenshot 2022-10-07 at 4 33 53 PM

    opened by muhammadadeel-10P 0
  • Unknown class _MDCOutlinedTextField in Interface Builder file.

    Unknown class _MDCOutlinedTextField in Interface Builder file.

    Getting unknown class exception when try to use use with story board.

    here are the steps

    1. Drag UITextfield into view change the class name to MDCOutlinedTextField identity inspector and Press enter
    2. Create IBOutlet in view controller swift class and connect them to textfield and run, It will works fine
    3. Now go to storyboard select textfield remove MDCOutlinedTextField from class name in identity inspector and press enter
    4. After that again add class name as MDCOutlinedTextField as a class name in identity inspector
    5. now it will crash and giving Unknown class _MDCOutlinedTextField in Interface Builder file.

    Full log is here

    2022-10-03 15:00:18.224135+0400 TestTextField[39660:448041] [Storyboard] Unknown class _TtC13TestTextField20MDCOutlinedTextField in Interface Builder file. 2022-10-03 15:00:18.230720+0400 TestTextField[39660:448041] -[UITextField label]: unrecognized selector sent to instance 0x7fcc2001ae00 2022-10-03 15:00:18.237268+0400 TestTextField[39660:448041] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[UITextField label]: unrecognized selector sent to instance 0x7fcc2001ae00'

    opened by gurumoorthy 1
  • MDCOutlinedTextField issue color in iOS 16

    MDCOutlinedTextField issue color in iOS 16

    I have an issue with my textflieds with:

    • Xcode 14.0.1
    • iOS 16
    • MaterialComponents (124.2.0)

    This is my theme config:

    // Colors for general behavior
        public let colorScheme: MDCContainerScheming = {
            let scheme = MDCContainerScheme()
            // The color displayed most frequently across your app’s screens and components
            scheme.colorScheme.primaryColor = UIColor.F.mainGreen()
            // A light or dark variation of the primary color.
            scheme.colorScheme.primaryColorVariant = UIColor.F.greenDark()
            // Text/iconography drawn on top of primaryColor
            scheme.colorScheme.onPrimaryColor = UIColor.F.whiteColor()
            // Provides ways to accent and distinguish your product. Floating action buttons use the secondary color.
            scheme.colorScheme.secondaryColor = UIColor.F.mainBlue()
            // Text/iconography drawn on top of secondaryColor
            scheme.colorScheme.onSecondaryColor = UIColor.F.whiteColor()
            // Typically maps to the background of components such as cards, sheets, and dialogs.
            scheme.colorScheme.surfaceColor = UIColor.F.backgroundColor()
            // Typically found behind scrollable content.
            scheme.colorScheme.backgroundColor = UIColor.F.backgroundColor()
            // Text/iconography drawn on top of backgroundColor
            scheme.colorScheme.onBackgroundColor = UIColor.F.titleColor()
            // The indication of errors within components such as text fields.
            scheme.colorScheme.errorColor = UIColor.F.mainRed()
            // Text/iconography drawn on top of surfaceColor.
            scheme.colorScheme.onSurfaceColor = UIColor.F.titleColor()
            return scheme
        }()
    

    For a second the background is black: https://user-images.githubusercontent.com/8509397/192558355-05af95ff-ca6d-4faa-a16f-84d1e4d90c2c.mov

    Anyone with this problem?

    opened by alexisbarnique 0
  • Build warning for MDFInternalization

    Build warning for MDFInternalization

    In my project, I am using Material TabbarView. I am using XCode 14 beta and seeing this warning:

    warning build: Run script build phase 'Create Symlinks to Header Folders' will be run during every build because it does not specify any outputs. To address this warning, either add output dependencies to the script phase, or configure it to run in every build by unchecking "Based on dependency analysis" in the script phase.

    opened by nithindevn 0
Releases(v124.2.0)
Owner
Material Components
Build beautiful, usable products with Material Components for Android, Flutter, iOS, and the web.
Material Components
Blobmorphism is a brand new design language I've created to break free of the material overload in iOS, built in SwiftUI. Everything feels smooth and fluid.

Blobmorphism is a brand new design language I've created to break free of the material overload in iOS, built in SwiftUI. Everything feels smooth and fluid.

Ethan Lipnik 89 Nov 29, 2022
A Material Design drop down for iOS

A Material Design drop down for iOS written in Swift. Demo Do pod try DropDown in your console and run the project to try a demo. To install CocoaPods

AssistoLab 2.3k Dec 20, 2022
A Swift material design UI module which paints over the parent view when the switch is on.

:octocat: ?? RAMPaperSwitch is a Swift material design UI module which paints over the parent view when the switch is turned on. iOS library by @Ramotion

Ramotion 2.9k Dec 29, 2022
Material, a UI/UX framework for creating beautiful iOS applications

Material Welcome to Material, a UI/UX framework for creating beautiful applications. Material's animation system has been completely reworked to take

Cosmicmind 12k Jan 2, 2023
A few drop-in SwiftUI components for easily importing and thumb-nailing files

FilesUI A few drop-in SwiftUI components for easily importing and thumb-nailing files Usage 1. Import Files To import files you can use the FileImport

Brianna Zamora 3 Oct 19, 2022
NotSwiftUI is designed to help you create UI components quickly and efficiently with code!

NotSwiftUI NotSwiftUI is designed to help you create UI components quickly and efficiently with code! Capitalizing on the idea that most of the UI ele

Jonathan G. 50 Dec 20, 2022
SwiftUI components and extensions that seem to be highly reusable

SwiftUI components and extensions that seem to be highly reusable

Yusuke Hosonuma 56 Dec 15, 2022
💾 A collection of classic-style UI components for iOS

A collection of classic-style UI components for UIKit, influenced by Windows 95 Introduction This is a little exploration into applying '90s-era desig

Blake Tsuzaki 2.2k Dec 22, 2022
It provides UI components such as popover, popup, dialog supporting iOS apps

Overview LCUIComponents is an on-going project, which supports creating transient views appearing above other content onscreen when a control is selec

Linh Chu 7 Apr 8, 2020
Spinner loader components with liquid animation

LiquidLoader LiquidLoader is the spinner loader UI components with liquid animation, inspired by Spinner Loader - Gooey light Effect [] (https://githu

Takuma Yoshida 1.3k Dec 21, 2022
SwiftUI: Components Library Inspired by Twitter's Bootstrap

bootswiftui SwiftUI: Components Library Inspired by Twitter's Bootstrap Warning This is just SwiftUI exercise. Please do not consider using this repo

Robert Sandru 1 Oct 27, 2022
Swift Package for distributing Mozilla's Rust-based application components

Swift Package for Mozilla's Rust Components This repository is a Swift Package for distributing releases of Mozilla's various Rust-based application c

Mozilla 19 Dec 30, 2022
A paging scroll view for SwiftUI, using internal SwiftUI components

PagingView A paging scroll view for SwiftUI, using internal SwiftUI components. This is basically the same as TabView in the paging mode with the inde

Eric Lewis 18 Dec 25, 2022
Protocol oriented, type safe, scalable design system foundation swift framework for iOS.

Doric: Design System Foundation Design System foundation written in Swift. Protocol oriented, type safe, scalable framework for iOS. Features Requirem

Jay 93 Dec 6, 2022
Electronic Design in Swithft

Edith Electronic design in Swithft Serendipitously, the first woman to be professionally employed as an electrical engineer in the United States was a

CIRCT 37 Nov 3, 2021
Simple and highly customizable iOS tag list view, in Swift.

TagListView Simple and highly customizable iOS tag list view, in Swift. Supports Storyboard, Auto Layout, and @IBDesignable. Usage The most convenient

Ela Workshop 2.5k Jan 5, 2023
A simple, customizable view for efficiently collecting country information in iOS apps.

CountryPickerView CountryPickerView is a simple, customizable view for selecting countries in iOS apps. You can clone/download the repository and run

Kizito Nwose 459 Dec 27, 2022
A customizable color picker for iOS in Swift

IGColorPicker is a fantastic color picker ?? written in Swift. Table of Contents Documentation Colors Style Other features Installation Example Gettin

iGenius 272 Dec 17, 2022
Customizable CheckBox / RadioButton component for iOS

GDCheckbox An easy to use CheckBox/Radio button component for iOS, with Attributes inspector support. Requirements Xcode 10+ Swift 5 iOS 9+ Installati

Saeid 23 Oct 8, 2022