[
  {
    "path": ".circleci/config.yml",
    "content": "version: 2\njobs:\n  build:\n    working_directory: ~/code\n    docker:\n      - image: circleci/android:api-29\n    environment:\n      JVM_OPTS: -Xmx3200m\n      MAX_RETRY: 4\n    steps:\n      - checkout\n      - restore_cache:\n          key: jars-{{ checksum \"build.gradle\" }}-{{ checksum  \"flexbox/build.gradle\" }}\n      - run:\n          name: Download Dependencies\n          command: ./gradlew androidDependencies\n      - run:\n          name: Set up gcloud service key\n          command: |\n            if [ -n \"$GCLOUD_SERVICE_KEY\" ]; then echo ${GCLOUD_SERVICE_KEY} | base64 --decode > ${HOME}/client-secret.json ;\n                gcloud config set project ${GCLOUD_PROJECT} ;\n                gcloud auth activate-service-account ${GCLOUD_SERVICE_ACCOUNT} --key-file ${HOME}/client-secret.json ;\n            fi\n      - save_cache:\n          paths:\n            - ~/.gradle\n          key: jars-{{ checksum \"build.gradle\" }}-{{ checksum  \"flexbox/build.gradle\" }}\n      - run:\n          name: Build apks\n          command: ./gradlew build assembleAndroidTest\n      - run:\n          name: Run Firebase Test Lab\n          command: |\n            if [ -n \"$GCLOUD_SERVICE_KEY\" ]; then set +e ;\n              counter=0 ;\n              result=1 ;\n              while [ $result != 0 -a $counter -lt $MAX_RETRY ]; do\n                gcloud firebase test android run \\\n                  --type instrumentation \\\n                  --app demo-playground/build/outputs/apk/debug/demo-playground-debug.apk \\\n                  --test flexbox/build/outputs/apk/androidTest/debug/flexbox-debug-androidTest.apk \\\n                  --device-ids hammerhead,sailfish \\\n                  --os-version-ids 19,21,23,24,25,26 \\\n                  --locales en --orientations portrait,landscape \\\n                  --results-bucket android-devrel-ci-flexbox \\\n                  --timeout 180s ;\n                result=$? ;\n                let counter=counter+1 ;\n              done\n              exit $result ;\n            fi\n"
  },
  {
    "path": ".github/issue_template.md",
    "content": "- [ ] I have searched [existing issues](https://github.com/google/flexbox-layout/issues) and confirmed this is not a duplicate\n\n## Issues and steps to reproduce\n*Please replace this with steps to reproduce your issue.*\n\n## Expected behavior\n*Please describe what you expected would happen.*\n\n## Version of the flexbox library\n*e.g. 0.2.6, 0.3.0-alpha3*\n\n## Link to code\n*Please link to the code we can use to reproduce this issue.*\n*A complete project we can build/run is preferred, if you can't provide one, please show*\n*us relevant code*\n"
  },
  {
    "path": ".github/workflows/gradle-wrapper-validation.yml",
    "content": "name: \"Validate Gradle Wrapper\"\non: [push, pull_request]\n\njobs:\n  validation:\n    name: \"Validation\"\n    runs-on: ubuntu-latest\n    steps:\n      - uses: actions/checkout@v2\n      - uses: gradle/wrapper-validation-action@v1\n"
  },
  {
    "path": ".gitignore",
    "content": "*.iml\n.gradle\n.idea/\n/local.properties\n/.idea/workspace.xml\n/.idea/libraries\n!.idea/codeStyleSettings.xml\n.DS_Store\n/build\n/captures\n.vscode/\n\n# Taken from Android.gitignore https://github.com/github/gitignore/blob/master/Android.gitignore\n#\n# Built application files\n*.apk\n*.ap_\n\n# Files for the Dalvik VM\n*.dex\n\n# Java class files\n*.class\n\n# Generated files\nbin/\ngen/\nout/\n\n# Gradle files\n.gradle/\nbuild/\n\n# Local configuration file (sdk path, etc)\nlocal.properties\n\n# Proguard folder generated by Eclipse\nproguard/\n\n# Log Files\n*.log\n\n# Android Studio Navigation editor temp files\n.navigation/\n\n# Android Studio captures folder\ncaptures/\n\n# Intellij\n*.iml\n"
  },
  {
    "path": "CONTRIBUTING.md",
    "content": "# How to become a contributor and submit your own code\n\n## Contributor License Agreements\n\nWe'd love to accept your sample apps and patches! Before we can take them, we\nhave to jump a couple of legal hurdles.\n\nPlease fill out either the individual or corporate Contributor License Agreement (CLA).\n\n  * If you are an individual writing original source code and you're sure you\n    own the intellectual property, then you'll need to sign an [individual CLA]\n    (https://cla.developers.google.com).\n  * If you work for a company that wants to allow you to contribute your work,\n    then you'll need to sign a [corporate CLA]\n    (https://cla.developers.google.com).\n\nFollow either of the two links above to access the appropriate CLA and\ninstructions for how to sign and return it. Once we receive it, we'll be able to\naccept your pull requests.\n\n## Contributing A Patch\n\n1. Submit an issue describing your proposed change to the repo in question.\n1. The repo owner will respond to your issue promptly.\n1. If your proposed change is accepted, and you haven't already done so, sign a\n   Contributor License Agreement (see details above).\n1. Fork the desired repo, develop and test your code changes.\n1. Ensure that your code adheres to the existing style in the sample to which\n   you are contributing. Refer to the\n   [Android Code Style Guide]\n   (https://source.android.com/source/code-style.html) for the\n   recommended coding standards for this organization.\n1. Ensure that your code has an appropriate set of unit tests which all pass.\n1. Submit a pull request.\n\n## Code Style\n\nThis repository follows the official Android code style.\nWhen you send a patch, please try to follow that.\nHere are the example steps to follow:\n\n1. From Android Studio or IntelliJ IDEA, navigate to \"Preferences\" -> \"Editor\" -> \"Code Style\"\n1. Select \"Import Scheme\" by clicking the gear icon next to the Scheme pull down\n1. Choose <root directory of flexbox-layout>/tool/codeStyleSettings.xml\n1. Create a new scheme by typing a scheme name in the \"To\" edit box or apply to the current scheme.\n"
  },
  {
    "path": "LICENSE",
    "content": "\n                                 Apache License\n                           Version 2.0, January 2004\n                        http://www.apache.org/licenses/\n\n   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION\n\n   1. Definitions.\n\n      \"License\" shall mean the terms and conditions for use, reproduction,\n      and distribution as defined by Sections 1 through 9 of this document.\n\n      \"Licensor\" shall mean the copyright owner or entity authorized by\n      the copyright owner that is granting the License.\n\n      \"Legal Entity\" shall mean the union of the acting entity and all\n      other entities that control, are controlled by, or are under common\n      control with that entity. For the purposes of this definition,\n      \"control\" means (i) the power, direct or indirect, to cause the\n      direction or management of such entity, whether by contract or\n      otherwise, or (ii) ownership of fifty percent (50%) or more of the\n      outstanding shares, or (iii) beneficial ownership of such entity.\n\n      \"You\" (or \"Your\") shall mean an individual or Legal Entity\n      exercising permissions granted by this License.\n\n      \"Source\" form shall mean the preferred form for making modifications,\n      including but not limited to software source code, documentation\n      source, and configuration files.\n\n      \"Object\" form shall mean any form resulting from mechanical\n      transformation or translation of a Source form, including but\n      not limited to compiled object code, generated documentation,\n      and conversions to other media types.\n\n      \"Work\" shall mean the work of authorship, whether in Source or\n      Object form, made available under the License, as indicated by a\n      copyright notice that is included in or attached to the work\n      (an example is provided in the Appendix below).\n\n      \"Derivative Works\" shall mean any work, whether in Source or Object\n      form, that is based on (or derived from) the Work and for which the\n      editorial revisions, annotations, elaborations, or other modifications\n      represent, as a whole, an original work of authorship. For the purposes\n      of this License, Derivative Works shall not include works that remain\n      separable from, or merely link (or bind by name) to the interfaces of,\n      the Work and Derivative Works thereof.\n\n      \"Contribution\" shall mean any work of authorship, including\n      the original version of the Work and any modifications or additions\n      to that Work or Derivative Works thereof, that is intentionally\n      submitted to Licensor for inclusion in the Work by the copyright owner\n      or by an individual or Legal Entity authorized to submit on behalf of\n      the copyright owner. For the purposes of this definition, \"submitted\"\n      means any form of electronic, verbal, or written communication sent\n      to the Licensor or its representatives, including but not limited to\n      communication on electronic mailing lists, source code control systems,\n      and issue tracking systems that are managed by, or on behalf of, the\n      Licensor for the purpose of discussing and improving the Work, but\n      excluding communication that is conspicuously marked or otherwise\n      designated in writing by the copyright owner as \"Not a Contribution.\"\n\n      \"Contributor\" shall mean Licensor and any individual or Legal Entity\n      on behalf of whom a Contribution has been received by Licensor and\n      subsequently incorporated within the Work.\n\n   2. Grant of Copyright License. Subject to the terms and conditions of\n      this License, each Contributor hereby grants to You a perpetual,\n      worldwide, non-exclusive, no-charge, royalty-free, irrevocable\n      copyright license to reproduce, prepare Derivative Works of,\n      publicly display, publicly perform, sublicense, and distribute the\n      Work and such Derivative Works in Source or Object form.\n\n   3. Grant of Patent License. Subject to the terms and conditions of\n      this License, each Contributor hereby grants to You a perpetual,\n      worldwide, non-exclusive, no-charge, royalty-free, irrevocable\n      (except as stated in this section) patent license to make, have made,\n      use, offer to sell, sell, import, and otherwise transfer the Work,\n      where such license applies only to those patent claims licensable\n      by such Contributor that are necessarily infringed by their\n      Contribution(s) alone or by combination of their Contribution(s)\n      with the Work to which such Contribution(s) was submitted. If You\n      institute patent litigation against any entity (including a\n      cross-claim or counterclaim in a lawsuit) alleging that the Work\n      or a Contribution incorporated within the Work constitutes direct\n      or contributory patent infringement, then any patent licenses\n      granted to You under this License for that Work shall terminate\n      as of the date such litigation is filed.\n\n   4. Redistribution. You may reproduce and distribute copies of the\n      Work or Derivative Works thereof in any medium, with or without\n      modifications, and in Source or Object form, provided that You\n      meet the following conditions:\n\n      (a) You must give any other recipients of the Work or\n          Derivative Works a copy of this License; and\n\n      (b) You must cause any modified files to carry prominent notices\n          stating that You changed the files; and\n\n      (c) You must retain, in the Source form of any Derivative Works\n          that You distribute, all copyright, patent, trademark, and\n          attribution notices from the Source form of the Work,\n          excluding those notices that do not pertain to any part of\n          the Derivative Works; and\n\n      (d) If the Work includes a \"NOTICE\" text file as part of its\n          distribution, then any Derivative Works that You distribute must\n          include a readable copy of the attribution notices contained\n          within such NOTICE file, excluding those notices that do not\n          pertain to any part of the Derivative Works, in at least one\n          of the following places: within a NOTICE text file distributed\n          as part of the Derivative Works; within the Source form or\n          documentation, if provided along with the Derivative Works; or,\n          within a display generated by the Derivative Works, if and\n          wherever such third-party notices normally appear. The contents\n          of the NOTICE file are for informational purposes only and\n          do not modify the License. You may add Your own attribution\n          notices within Derivative Works that You distribute, alongside\n          or as an addendum to the NOTICE text from the Work, provided\n          that such additional attribution notices cannot be construed\n          as modifying the License.\n\n      You may add Your own copyright statement to Your modifications and\n      may provide additional or different license terms and conditions\n      for use, reproduction, or distribution of Your modifications, or\n      for any such Derivative Works as a whole, provided Your use,\n      reproduction, and distribution of the Work otherwise complies with\n      the conditions stated in this License.\n\n   5. Submission of Contributions. Unless You explicitly state otherwise,\n      any Contribution intentionally submitted for inclusion in the Work\n      by You to the Licensor shall be under the terms and conditions of\n      this License, without any additional terms or conditions.\n      Notwithstanding the above, nothing herein shall supersede or modify\n      the terms of any separate license agreement you may have executed\n      with Licensor regarding such Contributions.\n\n   6. Trademarks. This License does not grant permission to use the trade\n      names, trademarks, service marks, or product names of the Licensor,\n      except as required for reasonable and customary use in describing the\n      origin of the Work and reproducing the content of the NOTICE file.\n\n   7. Disclaimer of Warranty. Unless required by applicable law or\n      agreed to in writing, Licensor provides the Work (and each\n      Contributor provides its Contributions) on an \"AS IS\" BASIS,\n      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n      implied, including, without limitation, any warranties or conditions\n      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A\n      PARTICULAR PURPOSE. You are solely responsible for determining the\n      appropriateness of using or redistributing the Work and assume any\n      risks associated with Your exercise of permissions under this License.\n\n   8. Limitation of Liability. In no event and under no legal theory,\n      whether in tort (including negligence), contract, or otherwise,\n      unless required by applicable law (such as deliberate and grossly\n      negligent acts) or agreed to in writing, shall any Contributor be\n      liable to You for damages, including any direct, indirect, special,\n      incidental, or consequential damages of any character arising as a\n      result of this License or out of the use or inability to use the\n      Work (including but not limited to damages for loss of goodwill,\n      work stoppage, computer failure or malfunction, or any and all\n      other commercial damages or losses), even if such Contributor\n      has been advised of the possibility of such damages.\n\n   9. Accepting Warranty or Additional Liability. While redistributing\n      the Work or Derivative Works thereof, You may choose to offer,\n      and charge a fee for, acceptance of support, warranty, indemnity,\n      or other liability obligations and/or rights consistent with this\n      License. However, in accepting such obligations, You may act only\n      on Your own behalf and on Your sole responsibility, not on behalf\n      of any other Contributor, and only if You agree to indemnify,\n      defend, and hold each Contributor harmless for any liability\n      incurred by, or claims asserted against, such Contributor by reason\n      of your accepting any such warranty or additional liability.\n\n   END OF TERMS AND CONDITIONS\n\n   APPENDIX: How to apply the Apache License to your work.\n\n      To apply the Apache License to your work, attach the following\n      boilerplate notice, with the fields enclosed by brackets \"[]\"\n      replaced with your own identifying information. (Don't include\n      the brackets!)  The text should be enclosed in the appropriate\n      comment syntax for the file format. We also recommend that a\n      file or class name and description of purpose be included on the\n      same \"printed page\" as the copyright notice for easier\n      identification within third-party archives.\n\n   Copyright 2018 Google LLC\n\n   Licensed under the Apache License, Version 2.0 (the \"License\");\n   you may not use this file except in compliance with the License.\n   You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n   Unless required by applicable law or agreed to in writing, software\n   distributed under the License is distributed on an \"AS IS\" BASIS,\n   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n   See the License for the specific language governing permissions and\n   limitations under the License.\n"
  },
  {
    "path": "README.md",
    "content": "# FlexboxLayout\n[ ![Circle CI](https://circleci.com/gh/google/flexbox-layout.svg?style=shield&circle-token=2a42716dfffab73d73c5ce7ed7b3ee620cfa137b) ](https://circleci.com/gh/google/flexbox-layout/tree/main)\n\nFlexboxLayout is a library project which brings the similar capabilities of\n[CSS Flexible Box Layout Module](https://www.w3.org/TR/css-flexbox-1) to Android.\n\n# Installation\nAdd the following dependency to your `build.gradle` file:\n\n```\ndependencies {\n    implementation 'com.google.android.flexbox:flexbox:3.0.0'\n}\n```\n\n**Starting from 3.0.0, the groupId is changed to `com.google.android.flexbox` in preparation to uploading the artifacts to google maven.\nYou can still download the artifacts from jcenter for the past versions with the prior groupId (`com.google.android`), but migrating the library 3.0.0 is recommended.**\n\nNote that the default values for `alignItems` and `alignContent` for `FlexboxLayout` have been changed from `stretch` to `flex_start` starting from 2.0.0, it may break the existing apps.\nPlease make sure to set `stretch` explicitly if you want to apply the behavior of `stretch`.\n\n\nNote that starting from 1.1.0, the library is expeced to use with AndroidX. Please migrate to [AndroidX](https://developer.android.com/jetpack/androidx/migrate) if you use 1.1.0 or above.\n\nPlease use 1.0.0 if you haven't migrated to AndroidX.\n\n\n# Usage\nThere are two ways of using Flexbox in your layout.\n\n## FlexboxLayout\nThe first one is `FlexboxLayout` that extends the `ViewGroup` like `LinearLayout` and `RelativeLayout`.\nYou can specify the attributes from a layout XML like:\n```xml\n<com.google.android.flexbox.FlexboxLayout\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"stretch\"\n    app:alignContent=\"stretch\" >\n\n    <TextView\n        android:id=\"@+id/textview1\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"80dp\"\n        app:layout_flexBasisPercent=\"50%\"\n        />\n\n    <TextView\n        android:id=\"@+id/textview2\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"80dp\"\n        app:layout_alignSelf=\"center\"\n        />\n\n    <TextView\n        android:id=\"@+id/textview3\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"80dp\"\n        app:layout_alignSelf=\"flex_end\"\n        />\n</com.google.android.flexbox.FlexboxLayout>\n```\n\nOr from code like:\n```java\nFlexboxLayout flexboxLayout = (FlexboxLayout) findViewById(R.id.flexbox_layout);\nflexboxLayout.setFlexDirection(FlexDirection.ROW);\n\nView view = flexboxLayout.getChildAt(0);\nFlexboxLayout.LayoutParams lp = (FlexboxLayout.LayoutParams) view.getLayoutParams();\nlp.setOrder(-1);\nlp.setFlexGrow(2);\nview.setLayoutParams(lp);\n```\n\n## FlexboxLayoutManager (within RecyclerView)\nThe second one is `FlexboxLayoutManager` that can be used within `RecyclerView`.\n\n```java\nRecyclerView recyclerView = (RecyclerView) context.findViewById(R.id.recyclerview);\nFlexboxLayoutManager layoutManager = new FlexboxLayoutManager(context);\nlayoutManager.setFlexDirection(FlexDirection.COLUMN);\nlayoutManager.setJustifyContent(JustifyContent.FLEX_END);\nrecyclerView.setLayoutManager(layoutManager);\n```\n\nor for the attributes for the children of the `FlexboxLayoutManager` you can do like:\n\n```java\nmImageView.setImageDrawable(drawable);\nViewGroup.LayoutParams lp = mImageView.getLayoutParams();\nif (lp instanceof FlexboxLayoutManager.LayoutParams) {\n    FlexboxLayoutManager.LayoutParams flexboxLp = (FlexboxLayoutManager.LayoutParams) lp;\n    flexboxLp.setFlexGrow(1.0f);\n    flexboxLp.setAlignSelf(AlignSelf.FLEX_END);\n}\n```\n\nThe advantage of using `FlexboxLayoutManager` is that it recycles the views that go off the screen\nfor reuse for the views that are appearing as the user scrolls instead of inflating every individual view,\nwhich consumes much less memory especially when the number of items contained in the Flexbox container is large.\n\n![FlexboxLayoutManager in action](/assets/flexbox-layoutmanager.gif)\n\n\n## Supported attributes/features comparison\nDue to some characteristics of `RecyclerView`, some Flexbox attributes are not available/not implemented\nto the `FlexboxLayoutManager`.\nHere is a quick overview of the attributes/features comparison between the two implementations.\n\n|Attribute / Feature|FlexboxLayout| FlexboxLayoutManager (RecyclerView)|\n| ------- |:-----------:|:----------------------------------:|\n|flexDirection|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|flexWrap|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png) (except `wrap_reverse`)|\n|justifyContent|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|alignItems|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|alignContent|![Check](/assets/pngs/check_green_small.png)| - |\n|layout_order|![Check](/assets/pngs/check_green_small.png)| - |\n|layout_flexGrow|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|layout_flexShrink|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|layout_alignSelf|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|layout_flexBasisPercent|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|layout_(min/max)Width|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|layout_(min/max)Height|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|layout_wrapBefore|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|Divider|![Check](/assets/pngs/check_green_small.png)|![Check](/assets/pngs/check_green_small.png)|\n|View recycling| - |![Check](/assets/pngs/check_green_small.png)|\n|Scrolling| *1 |![Check](/assets/pngs/check_green_small.png)|\n\n*1 Partially possible by wrapping it with `ScrollView`. But it isn't likely to work with a large set\n   of views inside the layout. Because it doesn't consider view recycling.\n\n# Supported attributes\n\n## Attributes for the FlexboxLayout:\n\n* __flexDirection__\n  * This attribute determines the direction of the main axis (and the cross axis, perpendicular to the main axis). The direction children items are placed inside the Flexbox layout.\n  Possible values are:\n    * row (default)\n    * row_reverse\n    * column\n    * column_reverse\n\n    ![Flex Direction explanation](/assets/flex-direction.gif)\n\n* __flexWrap__\n  * This attribute controls whether the flex container is single-line or multi-line, and the\n  direction of the cross axis. Possible values are:\n    * nowrap (default for FlexboxLayout)\n    * wrap (default for FlexboxLayoutManager)\n    * wrap_reverse (not supported by FlexboxLayoutManager)\n\n    ![Flex Wrap explanation](/assets/flex-wrap.gif)\n\n* __justifyContent__\n  * This attribute controls the alignment along the main axis. Possible values are:\n    * flex_start (default)\n    * flex_end\n    * center\n    * space_between\n    * space_around\n    * space_evenly\n\n    ![Justify Content explanation](/assets/justify-content.gif)\n\n* __alignItems__\n  * This attribute controls the alignment along the cross axis. Possible values are:\n    * flex_start (default for FlexboxLayout)\n    * flex_end\n    * center\n    * baseline\n    * stretch (default for FlexboxLayoutManager)\n\n    ![Align Items explanation](/assets/align-items.gif)\n\n* __alignContent__\n  * This attribute controls the alignment of the flex lines in the flex container. Possible values\n  are:\n    * flex_start (default)\n    * flex_end\n    * center\n    * space_between\n    * space_around\n    * stretch\n\n    ![Align Content explanation](/assets/align-content.gif)\n\n* __showDividerHorizontal__ (one or more of `none | beginning | middle | end`)\n* __dividerDrawableHorizontal__ (reference to a drawable)\n  * Puts horizontal dividers between flex lines (or flex items when flexDirection\n  is set to `column` or `column_rebase`).\n  \n* __showDividerVertical__ (one or more of `none | beginning | middle | end`)\n* __dividerDrawableVertical__ (reference to a drawable)\n  * Puts vertical dividers between flex items (or flex lines when flexDirection\n  is set to `column` or `column_rebase`).\n\n* __showDivider__ (one or more of `none | beginning | middle | end`)\n* __dividerDrawable__ (reference to a drawable)\n  * Shorthand for setting both horizontal and vertical dividers. Note that if used with other attributes\n  (such as `justifyContent=\"space_around\"` or `alignContent=\"space_between\"` ... etc) for putting \n  spaces between flex lines or flex items, you may see unexpected spaces. Please avoid using these\n  at the same time.\n  \n  Example of putting both vertical and horizontal dividers.\n  \n  `res/drawable/divider.xml`\n  ```xml\n  <shape xmlns:android=\"http://schemas.android.com/apk/res/android\">\n    <size\n        android:width=\"8dp\"\n        android:height=\"12dp\" />\n    <solid android:color=\"#44A444\" />\n  </shape> \n  ```\n  \n  `res/layout/content_main.xml`\n  ```xml\n  <com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:alignContent=\"flex_start\"\n    app:alignItems=\"flex_start\"\n    app:flexWrap=\"wrap\"\n    app:showDivider=\"beginning|middle\"\n    app:dividerDrawable=\"@drawable/divider\" >\n\n    <TextView\n        style=\"@style/FlexItem\"\n        android:layout_width=\"220dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\" />\n    <TextView\n        style=\"@style/FlexItem\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"2\" />\n    <TextView\n        style=\"@style/FlexItem\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\" />\n    <TextView\n        style=\"@style/FlexItem\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"4\" />\n    <TextView\n        style=\"@style/FlexItem\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"5\" />\n  ```\n  \n  ![Dividers beginning and middle](/assets/divider-beginning-middle.png)\n\n\n## Attributes for the children of a FlexboxLayout\n\n* __layout_order__ (integer)\n  * This attribute can change how the ordering of the children views are laid out.\n  By default, children are displayed and laid out in the same order as they appear in the\n  layout XML. If not specified, `1` is set as a default value.\n\n    ![Order explanation](/assets/layout_order.gif)\n\n* __layout_flexGrow__ (float)\n  * This attribute determines how much this child will grow if positive free space is\n  distributed relative to the rest of other flex items included in the same flex line.\n  If a flex item has a positive `layout_flexGrow` value, the item will take up the remaining\n  space in the flex line. If multiple flex items in the same flex line have positive `layout_flexGrow`\n  values, the remaining free space is distributed depending on the proportion of their declared\n  `layout_flexGrow` value. (Similar to the `layout_weight` attribute in the `LinearLayout`)\n  If not specified, `0` is set as a default value.\n\n    ![Flex Grow explanation](/assets/layout_flexGrow.gif)\n\n* __layout_flexShrink__ (float)\n  * This attribute determines how much this child will shrink if negative free space is\n  distributed relative to the rest of other flex items included in the same flex line.\n  If not specified, `1` is set as a default value.\n\n    ![Flex Shrink explanation](/assets/layout_flexShrink.gif)\n\n* __layout_alignSelf__\n  * This attribute determines the alignment along the cross axis (perpendicular to the\n  main axis). The alignment in the same direction can be determined by the\n  `alignItems` in the parent, but if this is set to other than\n  `auto`, the cross axis alignment is overridden for this child. Possible values are:\n    * auto (default)\n    * flex_start\n    * flex_end\n    * center\n    * baseline\n    * stretch\n\n    ![Align Self explanation](/assets/layout_alignSelf.gif)\n\n* __layout_flexBasisPercent__ (fraction)\n  * The initial flex item length in a fraction format relative to its parent.\n  The initial main size of this child view is trying to be expanded as the specified\n  fraction against the parent main size.\n  If this value is set, the length specified from `layout_width`\n  (or `layout_height`) is overridden by the calculated value from this attribute.\n  This attribute is only effective when the parent's length is definite (MeasureSpec mode is\n  `MeasureSpec.EXACTLY`). The default value is `-1`, which means not set.\n\n    ![Flex basis percent explanation](/assets/layout_flexBasisPercent.gif)\n\n* __layout_minWidth__ / __layout_minHeight__ (dimension)\n  * These attributes impose minimum size constraints for the children of FlexboxLayout.\n  A child view won't shrink less than the value of these attributes (varies based on the\n  `flexDirection` attribute as to which attribute imposes the size constraint along the\n  main axis) regardless of the `layout_flexShrink` attribute.\n\n    ![Min width explanation](/assets/layout_minWidth.gif)\n\n* __layout_maxWidth__ / __layout_maxHeight__ (dimension)\n  * These attributes impose maximum size constraints for the children of FlexboxLayout.\n  A child view won't be expanded more than the value of these attributes (varies based on the\n  `flexDirection` attribute as to which attribute imposes the size constraint along the\n  main axis) regardless of the `layout_flexGrow` attribute.\n\n    ![Max width explanation](/assets/layout_maxWidth.gif)\n\n* __layout_wrapBefore__ (boolean)\n  * This attribute forces a flex line wrapping, the default value is `false`.\n  i.e. if this is set to `true` for a\n  flex item, the item will become the first item of a flex line. (A wrapping happens\n  regardless of the flex items being processed in the previous flex line)\n  This attribute is ignored if the `flex_wrap` attribute is set to `nowrap`.\n  The equivalent attribute isn't defined in the original CSS Flexible Box Module\n  specification, but having this attribute is useful for Android developers. For example, to flatten\n  the layouts when building a grid-like layout or for a situation where developers want\n  to put a new flex line to make a semantic difference from the previous one, etc.\n\n    ![Wrap before explanation](/assets/layout_wrapBefore.gif)\n\n# Others\n\n## Known differences from the original CSS specification\nThis library tries to achieve the same capabilities of the original\n[Flexible Box specification](https://www.w3.org/TR/css-flexbox-1) as much as possible,\nbut due to some reasons such as the way specifying attributes can't be the same between\nCSS and Android XML, there are some known differences from the original specification.\n\n(1) There is no [flex-flow](https://www.w3.org/TR/css-flexbox-1/#flex-flow-property)\nequivalent attribute\n  * Because `flex-flow` is a shorthand for setting the `flex-direction` and `flex-wrap` properties,\n  specifying two attributes from a single attribute is not practical in Android.\n\n(2) There is no [flex](https://www.w3.org/TR/css-flexbox-1/#flex-property) equivalent attribute\n  * Likewise `flex` is a shorthand for setting the `flex-grow`, `flex-shrink` and `flex-basis`,\n  specifying those attributes from a single attribute is not practical.\n\n(3) `layout_flexBasisPercent` is introduced instead of\n  [flexBasis](https://www.w3.org/TR/css-flexbox-1/#flex-basis-property)\n  * Both `layout_flexBasisPercent` in this library and `flex-basis` property in the CSS are used to\n  determine the initial length of an individual flex item. The `flex-basis` property accepts width\n  values such as `1em`, `10px`, and `content` as strings as well as percentage values such as\n  `10%` and `30%`. `layout_flexBasisPercent` only accepts percentage values.\n  However, specifying initial fixed width values can be done by specifying width (or height) values in\n  layout_width (or layout_height, varies depending on the `flexDirection`). Also, the same\n  effect can be done by specifying \"wrap_content\" in layout_width (or layout_height) if\n  developers want to achieve the same effect as 'content'. Thus, `layout_flexBasisPercent` only\n  accepts percentage values, which can't be done through layout_width (or layout_height) for\n  simplicity.\n\n(4) `layout_wrapBefore` is introduced.\n  * The equivalent attribute doesn't exist in the CSS Flexible Box Module specification,\n  but as explained above, Android developers will benefit by having this attribute for having\n  more control over when a wrapping happens.\n\n(5) Default values for `alignItems` and `alignContent` are set to `flex_start` instead of `stretch`.\n  * Setting `stretch` for the `alignItems` is expensive because the children of `FlexboxLayout` are measured more than twice. The difference is more obvious when the layout hierarchy is deeply nested.\n\n## Xamarin Binding\nXamarin binding is now available on [NuGet](https://www.nuget.org/packages/FlexboxLayoutXamarinBindingAndroid/) thanks to [@btripp](https://github.com/btripp)\n\n## Demo apps\n### Flexbox Playground demo app\nThe `demo-playground` module works as a playground demo app for trying various values for the supported attributes.\nYou can install it by\n```\n./gradlew demo-playground:installDebug\n```\n\n### Cat gallery demo app\nThe `demo-cat-gallery` module showcases the usage of the FlexboxLayoutManager inside the RecyclerView\nthat handles various sizes of views aligned nicely regardless of the device width like the\nGoogle Photo app without loading all the images on the memory.\nThus compared to using the {@link FlexboxLayout}, it's much less likely to abuse the memory,\nwhich sometimes leads to the OutOfMemoryError.\n```\n./gradlew demo-cat-gallery:installDebug\n```\n\n## How to make contributions\nPlease read and follow the steps in [CONTRIBUTING.md](/CONTRIBUTING.md)\n\n## License\nPlease see [LICENSE](/LICENSE)\n"
  },
  {
    "path": "build.gradle",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\n// Top-level build file where you can add configuration options common to all sub-projects/modules.\n\nbuildscript {\n    ext {\n        minSdkVersion = 14\n        targetSdkVersion = 30\n        compileSdkVersion = 30\n\n        androidGradlePluginVersion = \"4.2.0\"\n        androidxAnnotationVersion = \"1.2.0\"\n        androidxAppCompatVersion = \"1.2.0\"\n        androidxCoreVersion = \"1.3.2\"\n        androidxPreferenceVersion = \"1.1.1\"\n        androidxRecyclerViewVersion = \"1.2.0\"\n        androidxEspressoVersion = \"3.3.0\"\n        androidxTestExtVersion = \"1.1.2\"\n        androidxTestVersion = \"1.3.0\"\n        junitVersion = \"4.13.2\"\n        kotlinVersion = \"1.4.32\"\n        materialVersion = \"1.3.0\"\n    }\n\n    repositories {\n        jcenter()\n        google()\n    }\n    dependencies {\n        classpath \"com.android.tools.build:gradle:$androidGradlePluginVersion\"\n        classpath \"org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlinVersion\"\n        // NOTE: Do not place your application dependencies here; they belong\n        // in the individual module build.gradle files\n    }\n}\n\nallprojects {\n    repositories {\n        jcenter()\n        google()\n    }\n}\n\ntask clean(type: Delete) {\n    delete rootProject.buildDir\n}\n\n// This allows to disable pre dexing. If not disabled, it makes each CI build slow\n// See https://circleci.com/docs/android/#disable-pre-dexing-to-improve-build-performance\n//     http://tools.android.com/tech-docs/new-build-system/tips#TOC-Improving-Build-Server-performance\nproject.ext.preDexLibs = !project.hasProperty('disablePreDex')\n\nsubprojects {\n    project.plugins.whenPluginAdded { plugin ->\n        if (\"com.android.build.gradle.AppPlugin\" == plugin.class.name) {\n            project.android.dexOptions.preDexLibraries = rootProject.ext.preDexLibs\n        } else if (\"com.android.build.gradle.LibraryPlugin\" == plugin.class.name) {\n            project.android.dexOptions.preDexLibraries = rootProject.ext.preDexLibs\n        }\n    }\n}\n"
  },
  {
    "path": "demo-cat-gallery/build.gradle",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\napply plugin: 'com.android.application'\napply plugin: 'kotlin-android'\n\nandroid {\n    compileSdkVersion rootProject.ext.compileSdkVersion\n\n    defaultConfig {\n        applicationId \"com.google.android.flexbox.apps.catgallery\"\n        minSdkVersion rootProject.ext.minSdkVersion\n        targetSdkVersion rootProject.ext.targetSdkVersion\n        versionCode 1\n        versionName \"1.0\"\n\n        testInstrumentationRunner \"androidx.test.runner.AndroidJUnitRunner\"\n    }\n    buildTypes {\n        release {\n            shrinkResources true\n            minifyEnabled true\n            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'\n        }\n    }\n}\n\ndependencies {\n    implementation project(path: \":flexbox\")\n    implementation \"androidx.appcompat:appcompat:${rootProject.androidxAppCompatVersion}\"\n    implementation \"androidx.recyclerview:recyclerview:${rootProject.androidxRecyclerViewVersion}\"\n    implementation \"com.google.android.material:material:${rootProject.materialVersion}\"\n    implementation \"org.jetbrains.kotlin:kotlin-stdlib:${rootProject.kotlinVersion}\"\n}\n"
  },
  {
    "path": "demo-cat-gallery/proguard-rules.pro",
    "content": "# Add project specific ProGuard rules here.\n# By default, the flags in this file are appended to flags specified\n# in /usr/local/google/home/thagikura/android-sdk/tools/proguard/proguard-android.txt\n# You can edit the include path and order by changing the proguardFiles\n# directive in build.gradle.\n#\n# For more details, see\n#   http://developer.android.com/guide/developing/tools/proguard.html\n\n# Add any project specific keep options here:\n\n# If your project uses WebView with JS, uncomment the following\n# and specify the fully qualified class name to the JavaScript interface\n# class:\n#-keepclassmembers class fqcn.of.javascript.interface.for.webview {\n#   public *;\n#}\n"
  },
  {
    "path": "demo-cat-gallery/src/main/AndroidManifest.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<manifest xmlns:android=\"http://schemas.android.com/apk/res/android\"\n          package=\"com.google.android.flexbox.apps.catgallery\">\n\n    <application\n        android:allowBackup=\"true\"\n        android:icon=\"@mipmap/ic_launcher\"\n        android:label=\"@string/app_name\"\n        android:supportsRtl=\"true\"\n        android:theme=\"@style/AppTheme\">\n        <activity\n            android:name=\".MainActivity\"\n            android:label=\"@string/app_name\"\n            android:theme=\"@style/AppTheme.NoActionBar\">\n            <intent-filter>\n                <action android:name=\"android.intent.action.MAIN\"/>\n\n                <category android:name=\"android.intent.category.LAUNCHER\"/>\n            </intent-filter>\n        </activity>\n    </application>\n\n</manifest>"
  },
  {
    "path": "demo-cat-gallery/src/main/java/com/google/android/flexbox/apps/catgallery/CatAdapter.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.apps.catgallery\n\nimport android.view.LayoutInflater\nimport android.view.ViewGroup\nimport androidx.recyclerview.widget.RecyclerView\n\n/**\n * Adapter class that handles the data set with the {@link RecyclerView.LayoutManager}\n */\ninternal class CatAdapter : RecyclerView.Adapter<CatViewHolder>() {\n\n    companion object {\n        private val CAT_IMAGE_IDS = intArrayOf(\n                R.drawable.cat_1,\n                R.drawable.cat_2,\n                R.drawable.cat_3,\n                R.drawable.cat_4,\n                R.drawable.cat_5,\n                R.drawable.cat_6,\n                R.drawable.cat_7,\n                R.drawable.cat_8,\n                R.drawable.cat_9,\n                R.drawable.cat_10,\n                R.drawable.cat_11,\n                R.drawable.cat_12,\n                R.drawable.cat_13,\n                R.drawable.cat_14,\n                R.drawable.cat_15,\n                R.drawable.cat_16,\n                R.drawable.cat_17,\n                R.drawable.cat_18,\n                R.drawable.cat_19\n        )\n    }\n\n    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): CatViewHolder {\n        val view = LayoutInflater.from(parent.context)\n                .inflate(R.layout.viewholder_cat, parent, false)\n        return CatViewHolder(view)\n    }\n\n    override fun onBindViewHolder(holder: CatViewHolder, position: Int) {\n        val pos = position % CAT_IMAGE_IDS.size\n        holder.bindTo(CAT_IMAGE_IDS[pos])\n    }\n\n    override fun getItemCount() = CAT_IMAGE_IDS.size * 4\n}\n"
  },
  {
    "path": "demo-cat-gallery/src/main/java/com/google/android/flexbox/apps/catgallery/CatViewHolder.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.apps.catgallery\n\nimport android.view.View\nimport android.widget.ImageView\nimport androidx.annotation.DrawableRes\nimport androidx.recyclerview.widget.RecyclerView\nimport com.google.android.flexbox.FlexboxLayoutManager\n\n/**\n * ViewHolder that represents a cat image.\n */\ninternal class CatViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {\n\n    private val imageView: ImageView = itemView.findViewById(R.id.imageview)\n\n    internal fun bindTo(@DrawableRes drawableRes: Int) {\n        imageView.setImageResource(drawableRes)\n        val lp = imageView.layoutParams\n        if (lp is FlexboxLayoutManager.LayoutParams) {\n            lp.flexGrow = 1f\n        }\n    }\n}\n"
  },
  {
    "path": "demo-cat-gallery/src/main/java/com/google/android/flexbox/apps/catgallery/MainActivity.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.apps.catgallery\n\nimport android.os.Bundle\nimport androidx.appcompat.app.AppCompatActivity\nimport androidx.appcompat.widget.Toolbar\nimport androidx.recyclerview.widget.RecyclerView\nimport com.google.android.flexbox.AlignItems\nimport com.google.android.flexbox.FlexDirection\nimport com.google.android.flexbox.FlexWrap\nimport com.google.android.flexbox.FlexboxLayoutManager\n\n/**\n * Launcher Activity for the cat gallery demo app that demonstrates the usage of the\n * {@link FlexboxLayoutManager} that handles various sizes of views aligned nicely regardless of\n * the device width like the Google Photo app without loading all the images on the memory.\n * Thus compared to using the {@link FlexboxLayout}, it's much less likely to abuse the memory,\n * which some times leads to the OutOfMemoryError.\n */\nclass MainActivity : AppCompatActivity() {\n\n    override fun onCreate(savedInstanceState: Bundle?) {\n        super.onCreate(savedInstanceState)\n        setContentView(R.layout.activity_main)\n\n        val toolbar: Toolbar = findViewById(R.id.toolbar)\n        setSupportActionBar(toolbar)\n\n        val flexboxLayoutManager = FlexboxLayoutManager(this).apply {\n            flexWrap = FlexWrap.WRAP\n            flexDirection = FlexDirection.ROW\n            alignItems = AlignItems.STRETCH\n        }\n\n        val recyclerView: RecyclerView = findViewById(R.id.recyclerview)\n        recyclerView.apply {\n            layoutManager = flexboxLayoutManager\n            adapter = CatAdapter()\n        }\n    }\n}\n"
  },
  {
    "path": "demo-cat-gallery/src/main/res/layout/activity_main.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<androidx.coordinatorlayout.widget.CoordinatorLayout\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:tools=\"http://schemas.android.com/tools\"\n    android:id=\"@+id/coordinator_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    android:fitsSystemWindows=\"true\"\n    tools:context=\"com.google.android.flexbox.apps.catgallery.MainActivity\">\n\n    <com.google.android.material.appbar.AppBarLayout\n        android:id=\"@+id/app_bar\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"@dimen/app_bar_height\"\n        android:fitsSystemWindows=\"true\"\n        android:theme=\"@style/AppTheme.AppBarOverlay\">\n\n        <com.google.android.material.appbar.CollapsingToolbarLayout\n            android:id=\"@+id/toolbar_layout\"\n            android:layout_width=\"match_parent\"\n            android:layout_height=\"match_parent\"\n            android:fitsSystemWindows=\"true\"\n            app:contentScrim=\"?attr/colorPrimary\"\n            app:layout_scrollFlags=\"scroll|enterAlwaysCollapsed\">\n\n            <androidx.appcompat.widget.Toolbar\n                android:id=\"@+id/toolbar\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"?attr/actionBarSize\"\n                app:layout_collapseMode=\"pin\"\n                app:popupTheme=\"@style/AppTheme.PopupOverlay\"/>\n\n        </com.google.android.material.appbar.CollapsingToolbarLayout>\n    </com.google.android.material.appbar.AppBarLayout>\n\n    <include layout=\"@layout/content_main\"/>\n\n</androidx.coordinatorlayout.widget.CoordinatorLayout>\n"
  },
  {
    "path": "demo-cat-gallery/src/main/res/layout/content_main.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<androidx.recyclerview.widget.RecyclerView\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    app:layout_behavior=\"@string/appbar_scrolling_view_behavior\"\n    android:id=\"@+id/recyclerview\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"/>\n"
  },
  {
    "path": "demo-cat-gallery/src/main/res/layout/viewholder_cat.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<ImageView\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/imageview\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"wrap_content\"\n    android:scaleType=\"centerCrop\"\n    android:layout_margin=\"1dp\"\n    android:contentDescription=\"@string/content_description_cat_view_holder\"/>\n"
  },
  {
    "path": "demo-cat-gallery/src/main/res/values/colors.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <color name=\"colorPrimary\">#3F51B5</color>\n    <color name=\"colorPrimaryDark\">#303F9F</color>\n    <color name=\"colorAccent\">#FF4081</color>\n</resources>\n"
  },
  {
    "path": "demo-cat-gallery/src/main/res/values/dimens.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <dimen name=\"app_bar_height\">180dp</dimen>\n</resources>\n"
  },
  {
    "path": "demo-cat-gallery/src/main/res/values/strings.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <string name=\"app_name\">Cat Gallery</string>\n    <string name=\"content_description_cat_view_holder\">Cat image</string>\n</resources>\n"
  },
  {
    "path": "demo-cat-gallery/src/main/res/values/styles.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n\n    <!-- Base application theme. -->\n    <style name=\"AppTheme\" parent=\"Theme.AppCompat.Light.DarkActionBar\">\n        <!-- Customize your theme here. -->\n        <item name=\"colorPrimary\">@color/colorPrimary</item>\n        <item name=\"colorPrimaryDark\">@color/colorPrimaryDark</item>\n        <item name=\"colorAccent\">@color/colorAccent</item>\n    </style>\n    <style name=\"AppTheme.NoActionBar\">\n        <item name=\"windowActionBar\">false</item>\n        <item name=\"windowNoTitle\">true</item>\n    </style>\n    <style name=\"AppTheme.AppBarOverlay\" parent=\"ThemeOverlay.AppCompat.Dark.ActionBar\"/>\n    <style name=\"AppTheme.PopupOverlay\" parent=\"ThemeOverlay.AppCompat.Light\"/>\n\n</resources>\n"
  },
  {
    "path": "demo-cat-gallery/src/main/res/values-v21/styles.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <style name=\"AppTheme.NoActionBar\">\n        <item name=\"windowActionBar\">false</item>\n        <item name=\"windowNoTitle\">true</item>\n        <item name=\"android:windowDrawsSystemBarBackgrounds\">true</item>\n        <item name=\"android:statusBarColor\">@android:color/transparent</item>\n    </style>\n</resources>\n"
  },
  {
    "path": "demo-playground/build.gradle",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\napply plugin: 'com.android.application'\napply plugin: 'kotlin-android'\n\nandroid {\n    compileSdkVersion rootProject.ext.compileSdkVersion\n\n    defaultConfig {\n        applicationId \"com.google.android.apps.flexbox\"\n        minSdkVersion rootProject.ext.minSdkVersion\n        targetSdkVersion rootProject.ext.targetSdkVersion\n        versionCode 1\n        versionName \"1.0\"\n\n        testInstrumentationRunner \"androidx.test.runner.AndroidJUnitRunner\"\n    }\n    buildTypes {\n        release {\n            shrinkResources true\n            minifyEnabled true\n            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'\n        }\n    }\n}\n\ndependencies {\n    implementation project(\":flexbox\")\n    implementation \"androidx.annotation:annotation:${rootProject.androidxAnnotationVersion}\"\n    implementation \"androidx.appcompat:appcompat:${rootProject.androidxAppCompatVersion}\"\n    implementation \"androidx.preference:preference:${rootProject.androidxPreferenceVersion}\"\n    implementation \"com.google.android.material:material:${rootProject.materialVersion}\"\n    implementation \"org.jetbrains.kotlin:kotlin-stdlib:$kotlinVersion\"\n\n    testImplementation \"junit:junit:${rootProject.ext.junitVersion}\"\n\n    androidTestImplementation \"androidx.annotation:annotation:${rootProject.androidxAnnotationVersion}\"\n    androidTestImplementation \"androidx.test:runner:${rootProject.androidxTestVersion}\"\n    androidTestImplementation \"androidx.test:rules:${rootProject.androidxTestVersion}\"\n    androidTestImplementation \"androidx.test.espresso:espresso-core:${rootProject.androidxEspressoVersion}\"\n}\n"
  },
  {
    "path": "demo-playground/proguard-rules.pro",
    "content": "#\n# Copyright 2016 Google Inc. All rights reserved.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n#      http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n#\n\n# Add project specific ProGuard rules here.\n# By default, the flags in this file are appended to flags specified\n# in ${sdk.dir}/tools/proguard/proguard-android.txt\n# You can edit the include path and order by changing the proguardFiles\n# directive in build.gradle.\n#\n# For more details, see\n#   http://developer.android.com/guide/developing/tools/proguard.html\n\n# Add any project specific keep options here:\n\n# If your project uses WebView with JS, uncomment the following\n# and specify the fully qualified class name to the JavaScript interface\n# class:\n#-keepclassmembers class fqcn.of.javascript.interface.for.webview {\n#   public *;\n#}\n"
  },
  {
    "path": "demo-playground/src/androidTest/java/com/google/android/apps/flexbox/test/MainActivityTest.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.apps.flexbox.test\n\nimport android.content.pm.ActivityInfo\nimport android.view.View\nimport android.widget.ArrayAdapter\nimport android.widget.RadioGroup\nimport android.widget.Spinner\nimport android.widget.TextView\nimport androidx.test.InstrumentationRegistry\nimport androidx.test.espresso.Espresso.onView\nimport androidx.test.espresso.action.ViewActions.*\nimport androidx.test.espresso.matcher.ViewMatchers.withId\nimport androidx.test.filters.FlakyTest\nimport androidx.test.filters.MediumTest\nimport androidx.test.rule.ActivityTestRule\nimport androidx.test.runner.AndroidJUnit4\nimport com.google.android.apps.flexbox.R\nimport com.google.android.flexbox.*\nimport com.google.android.material.navigation.NavigationView\nimport org.hamcrest.MatcherAssert.assertThat\nimport org.hamcrest.core.Is.`is`\nimport org.junit.Assert.*\nimport org.junit.Rule\nimport org.junit.Test\nimport org.junit.runner.RunWith\n\n/**\n * Integration tests for [MainActivity].\n */\n@RunWith(AndroidJUnit4::class)\n@MediumTest\nclass MainActivityTest {\n\n    @JvmField\n    @Rule\n    var activityRule = ActivityTestRule(MainActivity::class.java)\n\n    @Test\n    @FlakyTest\n    fun testAddFlexItem() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n        assertNotNull(flexboxLayout)\n        val beforeCount = flexboxLayout.childCount\n        onView(withId(R.id.add_fab)).perform(click())\n\n        assertThat(flexboxLayout.childCount, `is`(beforeCount + 1))\n    }\n\n    @Test\n    @FlakyTest\n    fun testRemoveFlexItem() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n        assertNotNull(flexboxLayout)\n        val beforeCount = flexboxLayout.childCount\n        onView(withId(R.id.remove_fab)).perform(click())\n\n        assertThat(flexboxLayout.childCount, `is`(beforeCount - 1))\n    }\n\n    @Test\n    @FlakyTest\n    fun testConfigurationChange() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n        assertNotNull(flexboxLayout)\n        onView(withId(R.id.add_fab)).perform(click())\n        onView(withId(R.id.add_fab)).perform(click())\n        onView(withId(R.id.add_fab)).perform(click())\n        val beforeCount = flexboxLayout.childCount\n\n        activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // Verify the flex items are restored across the configuration change.\n        assertThat(flexboxLayout.childCount, `is`(beforeCount))\n    }\n\n    @Test\n    @FlakyTest\n    fun testFlexDirectionSpinner() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n        assertNotNull(flexboxLayout)\n        val navigationView = activity.findViewById<NavigationView>(R.id.nav_view)\n        assertNotNull(navigationView)\n        val menu = navigationView.menu\n        val spinner = menu.findItem(R.id.menu_item_flex_direction).actionView as Spinner\n        val spinnerAdapter = spinner.adapter as ArrayAdapter<CharSequence>\n\n        val columnPosition = spinnerAdapter.getPosition(activity.getString(R.string.column))\n        activity.runOnUiThread { spinner.setSelection(columnPosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        val rowReversePosition = spinnerAdapter.getPosition(activity.getString(R.string.row_reverse))\n        activity.runOnUiThread { spinner.setSelection(rowReversePosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n    }\n\n    @Test\n    @FlakyTest\n    fun testFlexWrapSpinner() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n        assertNotNull(flexboxLayout)\n        val navigationView = activity.findViewById<NavigationView>(R.id.nav_view)\n        assertNotNull(navigationView)\n        val menu = navigationView.menu\n        val spinner = menu.findItem(R.id.menu_item_flex_wrap).actionView as Spinner\n        val spinnerAdapter = spinner.adapter as ArrayAdapter<CharSequence>\n\n        val wrapReversePosition = spinnerAdapter.getPosition(activity.getString(R.string.wrap_reverse))\n        activity.runOnUiThread { spinner.setSelection(wrapReversePosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP_REVERSE))\n\n        val noWrapPosition = spinnerAdapter.getPosition(activity.getString(R.string.nowrap))\n        activity.runOnUiThread { spinner.setSelection(noWrapPosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.NOWRAP))\n    }\n\n    @Test\n    @FlakyTest\n    fun testJustifyContentSpinner() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<View>(R.id.flexbox_layout) as FlexboxLayout\n        assertNotNull(flexboxLayout)\n        val navigationView = activity.findViewById<View>(R.id.nav_view) as NavigationView\n        assertNotNull(navigationView)\n        val menu = navigationView.menu\n        val spinner = menu.findItem(R.id.menu_item_justify_content).actionView as Spinner\n        val spinnerAdapter = spinner.adapter as ArrayAdapter<CharSequence>\n\n        val spaceBetweenPosition = spinnerAdapter.getPosition(activity.getString(R.string.space_between))\n        activity.runOnUiThread { spinner.setSelection(spaceBetweenPosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n\n        val centerPosition = spinnerAdapter.getPosition(activity.getString(R.string.center))\n        activity.runOnUiThread { spinner.setSelection(centerPosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.CENTER))\n    }\n\n    @Test\n    @FlakyTest\n    fun testAlignItemsSpinner() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n        assertNotNull(flexboxLayout)\n        val navigationView = activity.findViewById<NavigationView>(R.id.nav_view)\n        assertNotNull(navigationView)\n        val menu = navigationView.menu\n        val spinner = menu.findItem(R.id.menu_item_align_items).actionView as Spinner\n        val spinnerAdapter = spinner.adapter as ArrayAdapter<CharSequence>\n\n        val baselinePosition = spinnerAdapter.getPosition(activity.getString(R.string.baseline))\n        activity.runOnUiThread { spinner.setSelection(baselinePosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.BASELINE))\n\n        val flexEndPosition = spinnerAdapter.getPosition(activity.getString(R.string.flex_end))\n        activity.runOnUiThread { spinner.setSelection(flexEndPosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_END))\n    }\n\n    @Test\n    @FlakyTest\n    fun testAlignContentSpinner() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n        assertNotNull(flexboxLayout)\n        val navigationView = activity.findViewById<NavigationView>(R.id.nav_view)\n        assertNotNull(navigationView)\n        val menu = navigationView.menu\n        val spinner = menu.findItem(R.id.menu_item_align_content).actionView as Spinner\n        val spinnerAdapter = spinner.adapter as ArrayAdapter<CharSequence>\n\n        val spaceAroundPosition = spinnerAdapter.getPosition(activity.getString(R.string.space_around))\n        activity.runOnUiThread { spinner.setSelection(spaceAroundPosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.SPACE_AROUND))\n\n        val stretchPosition = spinnerAdapter.getPosition(activity.getString(R.string.stretch))\n        activity.runOnUiThread { spinner.setSelection(stretchPosition) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.STRETCH))\n    }\n\n    @Test\n    @FlakyTest\n    fun testEditFragment_changeOrder() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<View>(R.id.flexbox_layout) as FlexboxLayout\n        assertNotNull(flexboxLayout)\n        onView(withId(R.id.textview1)).perform(click())\n        onView(withId(R.id.edit_text_order)).perform(replaceText(\"3\"), closeSoftKeyboard())\n        onView(withId(R.id.button_ok)).perform(click())\n        val first = flexboxLayout.getReorderedChildAt(0) as TextView\n        val second = flexboxLayout.getReorderedChildAt(1) as TextView\n        val third = flexboxLayout.getReorderedChildAt(2) as TextView\n\n        assertThat(first.text.toString(), `is`(\"2\"))\n        assertThat(second.text.toString(), `is`(\"3\"))\n        assertThat(third.text.toString(), `is`(\"1\"))\n    }\n\n    @Test\n    @FlakyTest\n    fun testEditFragment_changeFlexGrow() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<View>(R.id.flexbox_layout) as FlexboxLayout\n        assertNotNull(flexboxLayout)\n        onView(withId(R.id.textview1)).perform(click())\n        onView(withId(R.id.edit_text_flex_grow)).perform(replaceText(\"1\"), closeSoftKeyboard())\n        onView(withId(R.id.button_ok)).perform(click())\n        val first = activity.findViewById<View>(R.id.textview1) as TextView\n        val second = activity.findViewById<View>(R.id.textview2) as TextView\n        val third = activity.findViewById<View>(R.id.textview3) as TextView\n        assertNotNull(first)\n        assertNotNull(second)\n        assertNotNull(third)\n\n        assertThat(first.width, `is`(flexboxLayout.width - second.width - third.width))\n    }\n\n    @Test\n    @FlakyTest\n    fun testEditFragment_changeFlexGrowFloat() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<View>(R.id.flexbox_layout) as FlexboxLayout\n        assertNotNull(flexboxLayout)\n        onView(withId(R.id.textview1)).perform(click())\n        onView(withId(R.id.edit_text_flex_grow)).perform(replaceText(\"1.0\"), closeSoftKeyboard())\n        onView(withId(R.id.button_ok)).perform(click())\n        val first = activity.findViewById<View>(R.id.textview1) as TextView\n        val second = activity.findViewById<View>(R.id.textview2) as TextView\n        val third = activity.findViewById<View>(R.id.textview3) as TextView\n        assertNotNull(first)\n        assertNotNull(second)\n        assertNotNull(third)\n\n        assertThat(first.width, `is`(flexboxLayout.width - second.width - third.width))\n    }\n\n    @Test\n    @FlakyTest\n    fun testEditFragment_changeFlexBasisPercent() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<View>(R.id.flexbox_layout) as FlexboxLayout\n        assertNotNull(flexboxLayout)\n        onView(withId(R.id.textview1)).perform(click())\n        onView(withId(R.id.edit_text_flex_basis_percent))\n                .perform(replaceText(\"50\"), closeSoftKeyboard())\n        onView(withId(R.id.button_ok)).perform(click())\n        val first = activity.findViewById<TextView>(R.id.textview1)\n        val second = activity.findViewById<TextView>(R.id.textview2)\n        val third = activity.findViewById<TextView>(R.id.textview3)\n        assertNotNull(first)\n        assertNotNull(second)\n        assertNotNull(third)\n\n        assertTrue(first.width - 1 <= flexboxLayout.width / 2 || flexboxLayout.width / 2 <= first.width + 1)\n    }\n\n    @Test\n    @FlakyTest\n    fun testSwitchRecyclerViewFragment() {\n        val activity = activityRule.activity\n        val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n        assertNotNull(flexboxLayout)\n        val navigationView = activity.findViewById<NavigationView>(R.id.nav_view)\n        assertNotNull(navigationView)\n        assertNull(activity.findViewById(R.id.recyclerview))\n        assertNotNull(activity.findViewById(R.id.flexbox_layout))\n\n        val radioGroup = navigationView.getHeaderView(0)\n                .findViewById<RadioGroup>(R.id.radiogroup_container_implementation)\n        activity.runOnUiThread { radioGroup.check(R.id.radiobutton_recyclerview) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertNotNull(activity.findViewById(R.id.recyclerview))\n        assertNull(activity.findViewById(R.id.flexbox_layout))\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/AndroidManifest.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<manifest xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:tools=\"http://schemas.android.com/tools\"\n    package=\"com.google.android.apps.flexbox\">\n\n    <uses-sdk tools:overrideLibrary=\"android.support.v14.preference\" />\n\n    <application\n        android:allowBackup=\"true\"\n        android:icon=\"@mipmap/ic_launcher\"\n        android:label=\"@string/app_name\"\n        android:supportsRtl=\"true\"\n        android:theme=\"@style/AppTheme\">\n        <activity\n            android:name=\"com.google.android.flexbox.MainActivity\"\n            android:label=\"@string/app_name\"\n            android:theme=\"@style/AppTheme.NoActionBar\">\n            <intent-filter>\n                <action android:name=\"android.intent.action.MAIN\" />\n\n                <category android:name=\"android.intent.category.LAUNCHER\" />\n            </intent-filter>\n        </activity>\n\n        <activity android:name=\"com.google.android.flexbox.SettingsActivity\" />\n    </application>\n\n</manifest>\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/Extensions.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.content.Context\n\n/**\n * Convert pixel to dp. Preserve the negative value as it's used for representing\n * MATCH_PARENT(-1) and WRAP_CONTENT(-2).\n * Ignore the round error that might happen in dividing the pixel by the density.\n *\n * @param pixel   the value in pixel\n *\n * @return the converted value in dp\n */\nfun Context.pixelToDp(pixel: Int): Int {\n    val displayMetrics = this.resources.displayMetrics\n    return if (pixel < 0) pixel else Math.round(pixel / displayMetrics.density)\n}\n\n/**\n * Convert dp to pixel. Preserve the negative value as it's used for representing\n * MATCH_PARENT(-1) and WRAP_CONTENT(-2).\n *\n * @param dp      the value in dp\n *\n * @return the converted value in pixel\n */\nfun Context.dpToPixel(dp: Int): Int {\n    val displayMetrics = this.resources.displayMetrics\n    return if (dp < 0) dp else Math.round(dp * displayMetrics.density)\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FlexItemAdapter.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.view.LayoutInflater\nimport android.view.ViewGroup\nimport androidx.appcompat.app.AppCompatActivity\nimport androidx.recyclerview.widget.RecyclerView\nimport com.google.android.apps.flexbox.R\n\n/**\n * [RecyclerView.Adapter] implementation for [FlexItemViewHolder].\n */\ninternal class FlexItemAdapter(private val activity: AppCompatActivity,\n                               private val flexContainer: FlexContainer)\n    : RecyclerView.Adapter<FlexItemViewHolder>() {\n\n    private val layoutParams = mutableListOf<FlexboxLayoutManager.LayoutParams>()\n\n    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): FlexItemViewHolder {\n        val view = LayoutInflater.from(parent.context)\n                .inflate(R.layout.viewholder_flex_item, parent, false)\n\n        return FlexItemViewHolder(view)\n    }\n\n    override fun onBindViewHolder(holder: FlexItemViewHolder, position: Int) {\n        val adapterPosition = holder.adapterPosition\n        // TODO: More optimized set the click listener inside the view holder\n        holder.itemView.setOnClickListener(FlexItemClickListener(activity,\n                FlexItemChangedListenerImplRecyclerView(flexContainer, this),\n                adapterPosition))\n        holder.bindTo(layoutParams[position])\n    }\n\n    fun addItem(lp: FlexboxLayoutManager.LayoutParams) {\n        layoutParams.add(lp)\n        notifyItemInserted(layoutParams.size - 1)\n    }\n\n    fun removeItem(position: Int) {\n        if (position < 0 || position >= layoutParams.size) {\n            return\n        }\n        layoutParams.removeAt(position)\n        notifyItemRemoved(layoutParams.size)\n        notifyItemRangeChanged(position, layoutParams.size)\n    }\n\n    val items get() = layoutParams\n\n    override fun getItemCount() = layoutParams.size\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FlexItemChangedListener.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\n/**\n * A listener that listens to the change of a flex item\n */\ninternal interface FlexItemChangedListener {\n\n    fun onFlexItemChanged(flexItem: FlexItem, viewIndex: Int)\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FlexItemChangedListenerImpl.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.view.ViewGroup\n\n/**\n * Default implementation for the [FlexItemChangedListener].\n */\ninternal class FlexItemChangedListenerImpl(private val flexContainer: FlexContainer) : FlexItemChangedListener {\n\n    override fun onFlexItemChanged(flexItem: FlexItem, viewIndex: Int) {\n        val view = flexContainer.getFlexItemAt(viewIndex)\n        view.layoutParams = flexItem as ViewGroup.LayoutParams\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FlexItemChangedListenerImplRecyclerView.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.view.ViewGroup\nimport androidx.recyclerview.widget.RecyclerView\n\n/**\n * Implementation for the [FlexItemChangedListener].\n * It expects RecyclerView as the underlying flex container implementation.\n */\ninternal class FlexItemChangedListenerImplRecyclerView(private val flexContainer: FlexContainer,\n                                              private val adapter: RecyclerView.Adapter<*>) : FlexItemChangedListener {\n\n    override fun onFlexItemChanged(flexItem: FlexItem, viewIndex: Int) {\n        val view = flexContainer.getFlexItemAt(viewIndex)\n        view.layoutParams = flexItem as ViewGroup.LayoutParams\n        adapter.notifyDataSetChanged()\n        // TODO: An Exception is thrown if notifyItemChanged(int) is used.\n        // Investigate that, but using LinearLayoutManager also produces the same Exception\n        // java.lang.IllegalArgumentException: Called attach on a child which is not detached:\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FlexItemClickListener.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.view.View\nimport androidx.appcompat.app.AppCompatActivity\n\n/**\n * Implementation of the [android.view.View.OnClickListener] when a flex item is clicked in\n * the Flexbox Playground demo app.\n */\ninternal class FlexItemClickListener(private val activity: AppCompatActivity, private val flexItemChangedListener: FlexItemChangedListener,\n                                     private val viewIndex: Int) : View.OnClickListener {\n\n    override fun onClick(v: View) =\n            FlexItemEditFragment.newInstance(v.layoutParams as FlexItem, viewIndex).apply {\n                setFlexItemChangedListener(flexItemChangedListener)\n            }.show(activity.supportFragmentManager, EDIT_DIALOG_TAG)\n\n    companion object {\n\n        private const val EDIT_DIALOG_TAG = \"edit_dialog_tag\"\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FlexItemEditFragment.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.content.Context\nimport android.os.Build\nimport android.os.Bundle\nimport android.text.Editable\nimport android.text.TextWatcher\nimport android.view.KeyEvent\nimport android.view.LayoutInflater\nimport android.view.View\nimport android.view.ViewGroup\nimport android.view.inputmethod.EditorInfo\nimport android.view.inputmethod.InputMethodManager\nimport android.widget.*\nimport androidx.fragment.app.DialogFragment\nimport com.google.android.apps.flexbox.R\nimport com.google.android.flexbox.validators.*\nimport com.google.android.material.textfield.TextInputLayout\n\n/**\n * DialogFragment that changes the properties for a flex item.\n */\ninternal class FlexItemEditFragment : DialogFragment() {\n\n    private lateinit var alignSelfAuto: String\n\n    private lateinit var alignSelfFlexStart: String\n\n    private lateinit var alignSelfFlexEnd: String\n\n    private lateinit var alignSelfCenter: String\n\n    private lateinit var alignSelfBaseline: String\n\n    private lateinit var alignSelfStretch: String\n\n    private var viewIndex: Int = 0\n\n    private lateinit var flexItem: FlexItem\n\n    /**\n     * Instance of a [FlexItem] being edited. At first it's created as another instance from\n     * the [flexItem] because otherwise changes before clicking the ok button will be\n     * reflected if the [flexItem] is changed directly.\n     */\n    private lateinit var flexItemInEdit: FlexItem\n\n    private var flexItemChangedListener: FlexItemChangedListener? = null\n\n    override fun onCreate(savedInstanceState: Bundle?) {\n        super.onCreate(savedInstanceState)\n        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {\n            setStyle(STYLE_NORMAL, android.R.style.Theme_Material_Light_Dialog)\n        } else {\n            setStyle(STYLE_NORMAL, android.R.style.Theme_Dialog)\n        }\n        arguments?.let {\n            flexItem = it.getParcelable(FLEX_ITEM_KEY)!!\n            viewIndex = it.getInt(VIEW_INDEX_KEY)\n        }\n        flexItemInEdit = createNewFlexItem(flexItem)\n\n        activity?.let {\n            alignSelfAuto = it.getString(R.string.auto)\n            alignSelfFlexStart = it.getString(R.string.flex_start)\n            alignSelfFlexEnd = it.getString(R.string.flex_end)\n            alignSelfCenter = it.getString(R.string.center)\n            alignSelfBaseline = it.getString(R.string.baseline)\n            alignSelfStretch = it.getString(R.string.stretch)\n        }\n    }\n\n    override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,\n                              savedInstanceState: Bundle?): View? {\n        val view = inflater.inflate(R.layout.fragment_flex_item_edit, container, false)\n        dialog?.setTitle((viewIndex + 1).toString())\n\n        val context = activity ?: return view\n        val orderTextInput: TextInputLayout = view.findViewById(R.id.input_layout_order)\n        val orderEdit: EditText = view.findViewById(R.id.edit_text_order)\n        orderEdit.setText(flexItem.order.toString())\n        orderEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, orderTextInput, IntegerInputValidator(),\n                        R.string.must_be_integer))\n        if (flexItem is FlexboxLayoutManager.LayoutParams) {\n            // Order is not enabled in FlexboxLayoutManager\n            orderEdit.isEnabled = false\n        }\n\n        val flexGrowInput: TextInputLayout = view .findViewById(R.id.input_layout_flex_grow)\n        val flexGrowEdit: EditText = view.findViewById(R.id.edit_text_flex_grow)\n        flexGrowEdit.setText(flexItem.flexGrow.toString())\n        flexGrowEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, flexGrowInput, NonNegativeDecimalInputValidator(),\n                        R.string.must_be_non_negative_float))\n\n        val flexShrinkInput: TextInputLayout = view.findViewById(R.id.input_layout_flex_shrink)\n        val flexShrinkEdit: EditText = view.findViewById(R.id.edit_text_flex_shrink)\n        flexShrinkEdit.setText(flexItem.flexShrink.toString())\n        flexShrinkEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, flexShrinkInput, NonNegativeDecimalInputValidator(),\n                        R.string.must_be_non_negative_float))\n\n        val flexBasisPercentInput: TextInputLayout =\n                view.findViewById(R.id.input_layout_flex_basis_percent)\n        val flexBasisPercentEdit: EditText = view.findViewById(R.id.edit_text_flex_basis_percent)\n        if (flexItem.flexBasisPercent != FlexboxLayout.LayoutParams.FLEX_BASIS_PERCENT_DEFAULT) {\n            flexBasisPercentEdit\n                    .setText(Math.round(flexItem.flexBasisPercent * 100).toString())\n        } else {\n            flexBasisPercentEdit.setText(flexItem.flexBasisPercent.toInt().toString())\n        }\n        flexBasisPercentEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, flexBasisPercentInput, FlexBasisPercentInputValidator(),\n                        R.string.must_be_minus_one_or_non_negative_integer))\n\n        val widthInput: TextInputLayout = view.findViewById(R.id.input_layout_width)\n        val widthEdit: EditText = view.findViewById(R.id.edit_text_width)\n        widthEdit.setText(context.pixelToDp(flexItem.width).toString())\n        widthEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, widthInput, DimensionInputValidator(),\n                        R.string.must_be_minus_one_or_minus_two_or_non_negative_integer))\n\n        val heightInput: TextInputLayout = view.findViewById(R.id.input_layout_height)\n        val heightEdit: EditText= view.findViewById(R.id.edit_text_height)\n        heightEdit.setText(context.pixelToDp(flexItem.height).toString())\n        heightEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, heightInput, DimensionInputValidator(),\n                        R.string.must_be_minus_one_or_minus_two_or_non_negative_integer))\n\n        val minWidthInput: TextInputLayout = view.findViewById(R.id.input_layout_min_width)\n        val minWidthEdit: EditText = view.findViewById(R.id.edit_text_min_width)\n        minWidthEdit.setText(context.pixelToDp(flexItem.minWidth).toString())\n        minWidthEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, minWidthInput, FixedDimensionInputValidator(),\n                        R.string.must_be_non_negative_integer))\n\n        val minHeightInput: TextInputLayout = view.findViewById(R.id.input_layout_min_height)\n        val minHeightEdit: EditText = view.findViewById(R.id.edit_text_min_height)\n        minHeightEdit.setText(context.pixelToDp(flexItem.minHeight).toString())\n        minHeightEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, minHeightInput, FixedDimensionInputValidator(),\n                        R.string.must_be_non_negative_integer))\n\n        val maxWidthInput: TextInputLayout = view.findViewById(R.id.input_layout_max_width)\n        val maxWidthEdit: EditText = view.findViewById(R.id.edit_text_max_width)\n        maxWidthEdit.setText(context.pixelToDp(flexItem.maxWidth).toString())\n        maxWidthEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, maxWidthInput, FixedDimensionInputValidator(),\n                        R.string.must_be_non_negative_integer))\n\n        val maxHeightInput: TextInputLayout = view.findViewById(R.id.input_layout_max_height)\n        val maxHeightEdit: EditText = view.findViewById(R.id.edit_text_max_height)\n        maxHeightEdit.setText(context.pixelToDp(flexItem.maxHeight).toString())\n        maxHeightEdit.addTextChangedListener(\n                FlexEditTextWatcher(context, maxHeightInput, FixedDimensionInputValidator(),\n                        R.string.must_be_non_negative_integer))\n\n        setNextFocusesOnEnterDown(orderEdit, flexGrowEdit, flexShrinkEdit, flexBasisPercentEdit,\n                widthEdit, heightEdit, minWidthEdit, minHeightEdit, maxWidthEdit, maxHeightEdit)\n\n        val alignSelfSpinner: Spinner = view.findViewById(R.id.spinner_align_self)\n        val arrayAdapter = ArrayAdapter.createFromResource(requireActivity(),\n                R.array.array_align_self, R.layout.spinner_item)\n        alignSelfSpinner.adapter = arrayAdapter\n        alignSelfSpinner.onItemSelectedListener = object : AdapterView.OnItemSelectedListener {\n            override fun onItemSelected(parent: AdapterView<*>, ignored: View?, position: Int,\n                                        id: Long) {\n                flexItemInEdit.alignSelf = when (parent.getItemAtPosition(position).toString()) {\n                    alignSelfAuto -> AlignSelf.AUTO\n                    alignSelfFlexStart -> AlignItems.FLEX_START\n                    alignSelfFlexEnd -> AlignItems.FLEX_END\n                    alignSelfCenter -> AlignItems.CENTER\n                    alignSelfBaseline -> AlignItems.BASELINE\n                    alignSelfStretch -> AlignItems.STRETCH\n                    else -> return\n                }\n            }\n\n            override fun onNothingSelected(parent: AdapterView<*>) {\n                // No op\n            }\n        }\n\n        val wrapBeforeCheckBox: CheckBox = view.findViewById(R.id.checkbox_wrap_before)\n        wrapBeforeCheckBox.isChecked = flexItem.isWrapBefore\n        wrapBeforeCheckBox.setOnCheckedChangeListener { _, isChecked ->\n            flexItemInEdit.isWrapBefore = isChecked }\n        val alignSelfPosition = arrayAdapter\n                .getPosition(alignSelfAsString(flexItem.alignSelf))\n        alignSelfSpinner.setSelection(alignSelfPosition)\n\n        view.findViewById<Button>(R.id.button_cancel).setOnClickListener {\n            copyFlexItemValues(flexItem, flexItemInEdit)\n            dismiss()\n        }\n        val okButton: Button = view.findViewById(R.id.button_ok)\n        okButton.setOnClickListener(View.OnClickListener {\n            if (orderTextInput.isErrorEnabled || flexGrowInput.isErrorEnabled ||\n                    flexBasisPercentInput.isErrorEnabled || widthInput.isErrorEnabled ||\n                    heightInput.isErrorEnabled || minWidthInput.isErrorEnabled ||\n                    minHeightInput.isErrorEnabled || maxWidthInput.isErrorEnabled ||\n                    maxHeightInput.isErrorEnabled) {\n                Toast.makeText(activity, R.string.invalid_values_exist, Toast.LENGTH_SHORT)\n                        .show()\n                return@OnClickListener\n            }\n            if (flexItemChangedListener != null) {\n                copyFlexItemValues(flexItemInEdit, flexItem)\n                flexItemChangedListener!!.onFlexItemChanged(flexItem, viewIndex)\n            }\n            dismiss()\n        })\n        return view\n    }\n\n    fun setFlexItemChangedListener(flexItemChangedListener: FlexItemChangedListener) {\n        this.flexItemChangedListener = flexItemChangedListener\n    }\n\n    private fun setNextFocusesOnEnterDown(vararg textViews: TextView) {\n        // This can be done by setting android:nextFocus* as in\n        // https://developer.android.com/training/keyboard-input/navigation.html\n        // But it requires API level 11 as a minimum sdk version. To support the lower level\n        // devices,\n        // doing it programmatically.\n        for (i in textViews.indices) {\n            textViews[i].setOnEditorActionListener { v, actionId, event ->\n                if (actionId == EditorInfo.IME_ACTION_NEXT ||\n                        actionId == EditorInfo.IME_ACTION_DONE ||\n                        actionId == EditorInfo.IME_NULL\n                                && event.action == KeyEvent.ACTION_DOWN\n                                && event.keyCode == KeyEvent.KEYCODE_ENTER) {\n                    if (i + 1 < textViews.size) {\n                        textViews[i + 1].requestFocus()\n                    } else if (i == textViews.size - 1) {\n                        val inputMethodManager = activity?.getSystemService(\n                                Context.INPUT_METHOD_SERVICE) as InputMethodManager?\n                        inputMethodManager?.hideSoftInputFromWindow(v.windowToken, 0)\n                    }\n                }\n                true\n            }\n\n            // Suppress the key focus change by KeyEvent.ACTION_UP of the enter key\n            textViews[i].setOnKeyListener { _, keyCode, event -> keyCode == KeyEvent.KEYCODE_ENTER && event.action == KeyEvent.ACTION_UP }\n        }\n\n    }\n\n    private fun alignSelfAsString(alignSelf: Int): String {\n        return when (alignSelf) {\n            AlignSelf.AUTO -> alignSelfAuto\n            AlignItems.FLEX_START -> alignSelfFlexStart\n            AlignItems.FLEX_END -> alignSelfFlexEnd\n            AlignItems.CENTER -> alignSelfCenter\n            AlignItems.BASELINE -> alignSelfBaseline\n            AlignItems.STRETCH -> alignSelfStretch\n            else -> alignSelfAuto\n        }\n    }\n\n    private inner class FlexEditTextWatcher internal constructor(val context: Context,\n                                                                 val textInputLayout: TextInputLayout,\n                                                                 val inputValidator: InputValidator,\n                                                                 val errorMessageId: Int) : TextWatcher {\n\n        override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {\n            // No op\n        }\n\n        override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) {\n            if (inputValidator.isValidInput(s)) {\n                textInputLayout.isErrorEnabled = false\n                textInputLayout.error = \"\"\n            } else {\n                textInputLayout.isErrorEnabled = true\n                textInputLayout.error = activity?.resources?.getString(errorMessageId)\n            }\n        }\n\n        override fun afterTextChanged(editable: Editable) {\n            if (textInputLayout.isErrorEnabled || editable.isEmpty() ||\n                    !inputValidator.isValidInput(editable.toString())) {\n                return\n            }\n            val value = editable.toString().toFloatOrNull() ?: return\n            when (textInputLayout.id) {\n                R.id.input_layout_order -> if (flexItemInEdit !is FlexboxLayoutManager.LayoutParams) {\n                    flexItemInEdit.order = value.toInt()\n                } else return\n                R.id.input_layout_flex_grow -> flexItemInEdit.flexGrow = value\n                R.id.input_layout_flex_shrink -> flexItemInEdit.flexShrink = value\n                R.id.input_layout_width -> flexItemInEdit.width = context.dpToPixel(value.toInt())\n                R.id.input_layout_height -> flexItemInEdit.height = context.dpToPixel(value.toInt())\n                R.id.input_layout_flex_basis_percent -> if (value != FlexboxLayout.LayoutParams.FLEX_BASIS_PERCENT_DEFAULT) {\n                    flexItemInEdit.flexBasisPercent = value.toInt() / 100.0f\n                } else {\n                    flexItemInEdit.flexBasisPercent = FlexItem.FLEX_BASIS_PERCENT_DEFAULT\n                }\n                R.id.input_layout_min_width -> flexItemInEdit.minWidth = context.dpToPixel(value.toInt())\n                R.id.input_layout_min_height -> flexItemInEdit.minHeight = context.dpToPixel(value.toInt())\n                R.id.input_layout_max_width -> flexItemInEdit.maxWidth = context.dpToPixel(value.toInt())\n                R.id.input_layout_max_height -> flexItemInEdit.maxHeight = context.dpToPixel(value.toInt())\n                else -> return\n            }\n        }\n    }\n\n    private fun createNewFlexItem(item: FlexItem): FlexItem {\n        if (item is FlexboxLayout.LayoutParams) {\n            val newItem = FlexboxLayout.LayoutParams(item.getWidth(), item.getHeight())\n            copyFlexItemValues(item, newItem)\n            return newItem\n        } else if (item is FlexboxLayoutManager.LayoutParams) {\n            val newItem = FlexboxLayoutManager.LayoutParams(item.getWidth(), item.getHeight())\n            copyFlexItemValues(item, newItem)\n            return newItem\n        }\n        throw IllegalArgumentException(\"Unknown FlexItem: $item\")\n    }\n\n    private fun copyFlexItemValues(from: FlexItem, to: FlexItem) {\n        if (from !is FlexboxLayoutManager.LayoutParams) {\n            to.order = from.order\n        }\n        to.flexGrow = from.flexGrow\n        to.flexShrink = from.flexShrink\n        to.flexBasisPercent = from.flexBasisPercent\n        to.height = from.height\n        to.width = from.width\n        to.maxHeight = from.maxHeight\n        to.minHeight = from.minHeight\n        to.maxWidth = from.maxWidth\n        to.minWidth = from.minWidth\n        to.alignSelf = from.alignSelf\n        to.isWrapBefore = from.isWrapBefore\n    }\n\n    companion object {\n\n        private const val FLEX_ITEM_KEY = \"flex_item\"\n\n        private const val VIEW_INDEX_KEY = \"view_index\"\n\n        fun newInstance(flexItem: FlexItem, viewIndex: Int) = FlexItemEditFragment().apply {\n            arguments = Bundle().apply {\n                putParcelable(FLEX_ITEM_KEY, flexItem)\n                putInt(VIEW_INDEX_KEY, viewIndex)\n            }\n        }\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FlexItemViewHolder.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.view.Gravity\nimport android.view.View\nimport android.widget.TextView\nimport androidx.recyclerview.widget.RecyclerView\nimport com.google.android.apps.flexbox.R\n\n/**\n * ViewHolder implementation for a flex item.\n */\nclass FlexItemViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {\n\n    private val textView: TextView = itemView.findViewById(R.id.textview)\n\n    fun bindTo(params: RecyclerView.LayoutParams) {\n        val adapterPosition = adapterPosition\n        textView.apply {\n            text = (adapterPosition + 1).toString()\n            setBackgroundResource(R.drawable.flex_item_background)\n            gravity = Gravity.CENTER\n            layoutParams = params\n        }\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FlexboxLayoutFragment.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.content.Context\nimport android.os.Bundle\nimport android.view.Gravity\nimport android.view.LayoutInflater\nimport android.view.View\nimport android.view.ViewGroup\nimport android.widget.TextView\nimport androidx.fragment.app.Fragment\nimport com.google.android.apps.flexbox.R\nimport com.google.android.material.floatingactionbutton.FloatingActionButton\nimport java.util.*\n\n/**\n * Fragment that contains the [FlexboxLayout] as the playground.\n */\nclass FlexboxLayoutFragment : Fragment() {\n\n    private lateinit var flexContainer: FlexboxLayout\n\n    override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,\n                              savedInstanceState: Bundle?): View? {\n        return inflater.inflate(R.layout.fragment_flexboxlayout, container, false)\n    }\n\n    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {\n        val activity = activity as MainActivity\n        flexContainer = view.findViewById(R.id.flexbox_layout)\n\n        val fragmentHelper = FragmentHelper(activity, flexContainer)\n        fragmentHelper.initializeViews()\n        if (savedInstanceState != null) {\n            val flexItems = savedInstanceState\n                    .getParcelableArrayList<FlexItem>(FLEX_ITEMS_KEY)!!\n            flexContainer.removeAllViews()\n            for (i in flexItems.indices) {\n                val flexItem = flexItems[i]\n                val textView = createBaseFlexItemTextView(activity, i)\n                textView.layoutParams = flexItem as FlexboxLayout.LayoutParams\n                flexContainer.addView(textView)\n            }\n        }\n        for (i in 0 until flexContainer.flexItemCount) {\n            flexContainer.getFlexItemAt(i).setOnClickListener(\n                    FlexItemClickListener(activity,\n                            FlexItemChangedListenerImpl(flexContainer), i))\n        }\n\n        val addFab: FloatingActionButton = activity.findViewById(R.id.add_fab)\n        addFab.setOnClickListener {\n            val viewIndex = flexContainer.flexItemCount\n            // index starts from 0. New View's index is N if N views ([0, 1, 2, ... N-1])\n            // exist.\n            val textView = createBaseFlexItemTextView(activity, viewIndex)\n            val lp = FlexboxLayout.LayoutParams(\n                    ViewGroup.LayoutParams.WRAP_CONTENT,\n                    ViewGroup.LayoutParams.WRAP_CONTENT)\n            fragmentHelper.setFlexItemAttributes(lp)\n            textView.layoutParams = lp\n            textView.setOnClickListener(FlexItemClickListener(activity,\n                    FlexItemChangedListenerImpl(flexContainer), viewIndex))\n            flexContainer.addView(textView)\n        }\n        val removeFab: FloatingActionButton = activity.findViewById(R.id.remove_fab)\n        removeFab.setOnClickListener(View.OnClickListener {\n            if (flexContainer.flexItemCount == 0) {\n                return@OnClickListener\n            }\n            flexContainer.removeViewAt(flexContainer.flexItemCount - 1)\n        })\n    }\n\n    override fun onSaveInstanceState(outState: Bundle) {\n        super.onSaveInstanceState(outState)\n        val flexItems = (0 until flexContainer.flexItemCount)\n                .map { flexContainer.getFlexItemAt(it) }\n                .mapTo(ArrayList()) { it.layoutParams as FlexItem }\n        outState.putParcelableArrayList(FLEX_ITEMS_KEY, flexItems)\n    }\n\n    private fun createBaseFlexItemTextView(context: Context, index: Int): TextView {\n        return TextView(context).apply {\n            setBackgroundResource(R.drawable.flex_item_background)\n            text = (index + 1).toString()\n            gravity = Gravity.CENTER\n        }\n    }\n\n    companion object {\n\n        private const val FLEX_ITEMS_KEY = \"flex_items_key\"\n\n        fun newInstance(): FlexboxLayoutFragment {\n            return FlexboxLayoutFragment()\n        }\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/FragmentHelper.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.content.SharedPreferences\nimport android.view.Menu\nimport android.view.View\nimport android.widget.AdapterView\nimport android.widget.ArrayAdapter\nimport android.widget.Spinner\nimport android.widget.Toast\nimport androidx.preference.PreferenceManager\nimport com.google.android.apps.flexbox.R\nimport com.google.android.material.navigation.NavigationView\n\n/**\n * Helper class that has the common logic for initializing the Fragment for the play ground demo\n * such as [FlexboxLayoutFragment] and a Fragment that uses RecyclerView in it.\n */\ninternal class FragmentHelper(private val activity: MainActivity, private val flexContainer: FlexContainer) {\n\n    private lateinit var ROW: String\n\n    private lateinit var COLUMN: String\n\n    private lateinit var ROW_REVERSE: String\n\n    private lateinit var COLUMN_REVERSE: String\n\n    private lateinit var NOWRAP: String\n\n    private lateinit var WRAP: String\n\n    private lateinit var WRAP_REVERSE: String\n\n    private lateinit var FLEX_START: String\n\n    private lateinit var FLEX_END: String\n\n    private lateinit var CENTER: String\n\n    private lateinit var BASELINE: String\n\n    private lateinit var STRETCH: String\n\n    private lateinit var SPACE_BETWEEN: String\n\n    private lateinit var SPACE_AROUND: String\n\n    private lateinit var SPACE_EVENLY: String\n\n    private lateinit var sharedPreferences: SharedPreferences\n\n    fun initializeViews() {\n        sharedPreferences = PreferenceManager.getDefaultSharedPreferences(activity)\n        initializeStringResources()\n        val navigationView: NavigationView = activity.findViewById(R.id.nav_view)\n        navigationView.setNavigationItemSelectedListener(activity)\n        val navigationMenu = navigationView.menu\n        initializeFlexDirectionSpinner(navigationMenu)\n        initializeFlexWrapSpinner(navigationMenu)\n        initializeJustifyContentSpinner(navigationMenu)\n        initializeAlignItemsSpinner(navigationMenu)\n        initializeAlignContentSpinner(navigationMenu)\n    }\n\n    private fun initializeStringResources() {\n        ROW = activity.getString(R.string.row)\n        COLUMN = activity.getString(R.string.column)\n        ROW_REVERSE = activity.getString(R.string.row_reverse)\n        COLUMN_REVERSE = activity.getString(R.string.column_reverse)\n        NOWRAP = activity.getString(R.string.nowrap)\n        WRAP = activity.getString(R.string.wrap)\n        WRAP_REVERSE = activity.getString(R.string.wrap_reverse)\n        FLEX_START = activity.getString(R.string.flex_start)\n        FLEX_END = activity.getString(R.string.flex_end)\n        CENTER = activity.getString(R.string.center)\n        BASELINE = activity.getString(R.string.baseline)\n        STRETCH = activity.getString(R.string.stretch)\n        SPACE_BETWEEN = activity.getString(R.string.space_between)\n        SPACE_AROUND = activity.getString(R.string.space_around)\n        SPACE_EVENLY = activity.getString(R.string.space_evenly)\n    }\n\n    /**\n     * Sets the attributes for a [FlexItem] based on the stored default values in\n     * the SharedPreferences.\n\n     * @param flexItem the FlexItem instance\n     * *\n     * @return a FlexItem instance, which attributes from the SharedPreferences are updated\n     */\n    fun setFlexItemAttributes(flexItem: FlexItem): FlexItem {\n        flexItem.width = activity.dpToPixel(readPreferenceAsInteger(activity.getString(R.string.new_width_key), DEFAULT_WIDTH))\n        flexItem.height = activity.dpToPixel(readPreferenceAsInteger(activity.getString(R.string.new_height_key), DEFAULT_HEIGHT))\n        // Order is not supported in the FlexboxLayoutManager\n        if (flexItem !is FlexboxLayoutManager.LayoutParams) {\n            flexItem.order = readPreferenceAsInteger(activity.getString(R.string.new_flex_item_order_key), \"1\")\n        }\n        flexItem.flexGrow = readPreferenceAsFloat(activity.getString(R.string.new_flex_grow_key), \"0.0\")\n        flexItem.flexShrink = readPreferenceAsFloat(activity.getString(R.string.new_flex_shrink_key), \"1.0\")\n        val flexBasisPercent = readPreferenceAsInteger(\n                activity.getString(R.string.new_flex_basis_percent_key), \"-1\")\n        flexItem.flexBasisPercent = if (flexBasisPercent == -1) -1f else (flexBasisPercent / 100.0).toFloat()\n        return flexItem\n    }\n\n    private fun readPreferenceAsInteger(key: String, defValue: String): Int {\n        return if (sharedPreferences.contains(key)) {\n            sharedPreferences.getString(key, defValue)?.toIntOrNull() ?: defValue.toInt()\n        } else {\n            defValue.toInt()\n        }\n    }\n\n    private fun readPreferenceAsFloat(key: String, defValue: String): Float {\n        return if (sharedPreferences.contains(key)) {\n            sharedPreferences.getString(key, defValue)?.toFloatOrNull() ?: defValue.toFloat()\n        } else {\n            defValue.toFloat()\n        }\n    }\n\n    private fun initializeSpinner(currentValue: Int, menuItemId: Int, navigationMenu: Menu,\n                                  arrayResourceId: Int, listener: AdapterView.OnItemSelectedListener,\n                                  converter: ValueToStringConverter) {\n        val spinner = navigationMenu.findItem(menuItemId).actionView as Spinner\n        val adapter = ArrayAdapter.createFromResource(activity,\n                arrayResourceId, R.layout.spinner_item)\n        spinner.adapter = adapter\n        spinner.onItemSelectedListener = listener\n        val selectedAsString = converter.asString(currentValue)\n        val position = adapter.getPosition(selectedAsString)\n        spinner.setSelection(position)\n    }\n\n    private fun initializeFlexDirectionSpinner(navigationMenu: Menu) {\n        initializeSpinner(flexContainer.flexDirection, R.id.menu_item_flex_direction,\n                navigationMenu, R.array.array_flex_direction,\n                object : AdapterView.OnItemSelectedListener {\n                    override fun onItemSelected(parent: AdapterView<*>, ignored: View?, position: Int,\n                                                id: Long) {\n                        flexContainer.flexDirection = when (parent.getItemAtPosition(position).toString()) {\n                            ROW -> FlexDirection.ROW\n                            ROW_REVERSE -> FlexDirection.ROW_REVERSE\n                            COLUMN -> FlexDirection.COLUMN\n                            COLUMN_REVERSE -> FlexDirection.COLUMN_REVERSE\n                            else -> return\n                        }\n                    }\n\n                    override fun onNothingSelected(parent: AdapterView<*>) {\n                        // No op\n                    }\n                }, object : ValueToStringConverter {\n            override fun asString(value: Int): String {\n                return when (value) {\n                    FlexDirection.ROW -> ROW\n                    FlexDirection.ROW_REVERSE -> ROW_REVERSE\n                    FlexDirection.COLUMN -> COLUMN\n                    FlexDirection.COLUMN_REVERSE -> COLUMN_REVERSE\n                    else -> ROW\n                }\n            }\n        })\n    }\n\n    private fun initializeFlexWrapSpinner(navigationMenu: Menu) {\n        initializeSpinner(flexContainer.flexWrap, R.id.menu_item_flex_wrap,\n                navigationMenu, R.array.array_flex_wrap,\n                object : AdapterView.OnItemSelectedListener {\n                    override fun onItemSelected(parent: AdapterView<*>, ignored: View?, position: Int,\n                                                id: Long) {\n                        flexContainer.flexWrap = when (parent.getItemAtPosition(position).toString()) {\n                            NOWRAP -> FlexWrap.NOWRAP\n                            WRAP -> FlexWrap.WRAP\n                            WRAP_REVERSE -> if (flexContainer is FlexboxLayoutManager) {\n                                Toast.makeText(activity,\n                                        R.string.wrap_reverse_not_supported,\n                                        Toast.LENGTH_SHORT).show()\n                                return\n                            } else {\n                                FlexWrap.WRAP_REVERSE\n                            }\n                            else -> return\n                        }\n                    }\n\n                    override fun onNothingSelected(parent: AdapterView<*>) {\n                        // No op\n                    }\n                }, object : ValueToStringConverter {\n            override fun asString(value: Int): String {\n                return when (value) {\n                    FlexWrap.NOWRAP -> NOWRAP\n                    FlexWrap.WRAP -> WRAP\n                    FlexWrap.WRAP_REVERSE -> WRAP_REVERSE\n                    else -> NOWRAP\n                }\n            }\n        })\n    }\n\n    private fun initializeJustifyContentSpinner(navigationMenu: Menu) {\n        initializeSpinner(flexContainer.justifyContent, R.id.menu_item_justify_content,\n                navigationMenu, R.array.array_justify_content,\n                object : AdapterView.OnItemSelectedListener {\n                    override fun onItemSelected(parent: AdapterView<*>, ignored: View?, position: Int,\n                                                id: Long) {\n                        flexContainer.justifyContent = when (parent.getItemAtPosition(position).toString()) {\n                            FLEX_START -> JustifyContent.FLEX_START\n                            FLEX_END -> JustifyContent.FLEX_END\n                            CENTER -> JustifyContent.CENTER\n                            SPACE_BETWEEN -> JustifyContent.SPACE_BETWEEN\n                            SPACE_AROUND -> JustifyContent.SPACE_AROUND\n                            SPACE_EVENLY -> JustifyContent.SPACE_EVENLY\n                            else -> return\n                        }\n                    }\n\n                    override fun onNothingSelected(parent: AdapterView<*>) {\n                        // No op\n                    }\n                }, object : ValueToStringConverter {\n            override fun asString(value: Int): String {\n                return when (value) {\n                    JustifyContent.FLEX_START -> FLEX_START\n                    JustifyContent.FLEX_END -> FLEX_END\n                    JustifyContent.CENTER -> CENTER\n                    JustifyContent.SPACE_AROUND -> SPACE_AROUND\n                    JustifyContent.SPACE_BETWEEN -> SPACE_BETWEEN\n                    JustifyContent.SPACE_EVENLY -> SPACE_EVENLY\n                    else -> FLEX_START\n                }\n            }\n        })\n    }\n\n    private fun initializeAlignItemsSpinner(navigationMenu: Menu) {\n        initializeSpinner(flexContainer.alignItems, R.id.menu_item_align_items,\n                navigationMenu, R.array.array_align_items,\n                object : AdapterView.OnItemSelectedListener {\n                    override fun onItemSelected(parent: AdapterView<*>, ignored: View?, position: Int,\n                                                id: Long) {\n                        flexContainer.alignItems = when (parent.getItemAtPosition(position).toString()) {\n                            FLEX_START -> AlignItems.FLEX_START\n                            FLEX_END -> AlignItems.FLEX_END\n                            CENTER -> AlignItems.CENTER\n                            BASELINE -> AlignItems.BASELINE\n                            STRETCH -> AlignItems.STRETCH\n                            else -> return\n                        }\n                    }\n\n                    override fun onNothingSelected(parent: AdapterView<*>) {\n                        // No op\n                    }\n                }, object : ValueToStringConverter {\n            override fun asString(value: Int): String {\n                return when (value) {\n                    AlignItems.FLEX_START -> FLEX_START\n                    AlignItems.FLEX_END -> FLEX_END\n                    AlignItems.CENTER -> CENTER\n                    AlignItems.BASELINE -> BASELINE\n                    AlignItems.STRETCH -> STRETCH\n                    else -> STRETCH\n                }\n            }\n        })\n    }\n\n    private fun initializeAlignContentSpinner(navigationMenu: Menu) {\n        initializeSpinner(flexContainer.alignContent, R.id.menu_item_align_content,\n                navigationMenu, R.array.array_align_content,\n                object : AdapterView.OnItemSelectedListener {\n                    override fun onItemSelected(parent: AdapterView<*>, ignored: View?, position: Int,\n                                                id: Long) {\n                        if (flexContainer is FlexboxLayoutManager) {\n                            Toast.makeText(activity, R.string.align_content_not_supported,\n                                    Toast.LENGTH_SHORT).show()\n                            return\n                        }\n                        flexContainer.alignContent = when (parent.getItemAtPosition(position).toString()) {\n                            FLEX_START -> AlignContent.FLEX_START\n                            FLEX_END -> AlignContent.FLEX_END\n                            CENTER -> AlignContent.CENTER\n                            SPACE_BETWEEN -> AlignContent.SPACE_BETWEEN\n                            SPACE_AROUND -> AlignContent.SPACE_AROUND\n                            STRETCH -> AlignContent.STRETCH\n                            else -> return\n                        }\n                    }\n\n                    override fun onNothingSelected(parent: AdapterView<*>) {\n                        // No op\n                    }\n                }, object : ValueToStringConverter {\n            override fun asString(value: Int): String {\n                when (value) {\n                    AlignContent.FLEX_START -> return FLEX_START\n                    AlignContent.FLEX_END -> return FLEX_END\n                    AlignContent.CENTER -> return CENTER\n                    AlignContent.SPACE_BETWEEN -> return SPACE_BETWEEN\n                    AlignContent.SPACE_AROUND -> return SPACE_AROUND\n                    AlignContent.STRETCH -> return STRETCH\n                    else -> return STRETCH\n                }\n            }\n        })\n    }\n\n    /**\n     * Converter for converting an int value for Flexbox properties to a String.\n     */\n    private interface ValueToStringConverter {\n\n        fun asString(value: Int): String\n    }\n\n    companion object {\n\n        private const val DEFAULT_WIDTH = \"120\"\n\n        private const val DEFAULT_HEIGHT = \"80\"\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/MainActivity.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.content.Intent\nimport android.os.Bundle\nimport android.view.Menu\nimport android.view.MenuItem\nimport android.widget.RadioGroup\nimport androidx.appcompat.app.ActionBarDrawerToggle\nimport androidx.appcompat.app.AppCompatActivity\nimport androidx.appcompat.widget.Toolbar\nimport androidx.drawerlayout.widget.DrawerLayout\nimport androidx.fragment.app.FragmentManager\nimport com.google.android.apps.flexbox.R\nimport com.google.android.material.navigation.NavigationView\n\nclass MainActivity : AppCompatActivity(), NavigationView.OnNavigationItemSelectedListener {\n\n    override fun onCreate(savedInstanceState: Bundle?) {\n        super.onCreate(savedInstanceState)\n        setContentView(R.layout.activity_main)\n\n        val toolbar: Toolbar = findViewById(R.id.toolbar)\n        setSupportActionBar(toolbar)\n        val drawer: DrawerLayout = findViewById(R.id.drawer_layout)\n        val toggle = ActionBarDrawerToggle(\n                this, drawer, toolbar, R.string.navigation_drawer_open,\n                R.string.navigation_drawer_close)\n        drawer.addDrawerListener(toggle)\n        toggle.syncState()\n\n        val navigationView: NavigationView = findViewById(R.id.nav_view)\n        val radioGroup: RadioGroup = navigationView.getHeaderView(0)\n                .findViewById(R.id.radiogroup_container_implementation)\n        val fragmentManager = supportFragmentManager\n\n        radioGroup.setOnCheckedChangeListener { _, checkedId ->\n            if (checkedId == R.id.radiobutton_viewgroup) {\n                replaceToFlexboxLayoutFragment(fragmentManager)\n            } else {\n                replaceToRecyclerViewFragment(fragmentManager)\n            }\n        }\n\n        if (savedInstanceState == null) {\n            replaceToFlexboxLayoutFragment(fragmentManager)\n        }\n    }\n\n    private fun replaceToFlexboxLayoutFragment(fragmentManager: FragmentManager) {\n        var fragment: FlexboxLayoutFragment? = fragmentManager.findFragmentByTag(FLEXBOXLAYOUT_FRAGMENT) as FlexboxLayoutFragment?\n        if (fragment == null) {\n            fragment = FlexboxLayoutFragment.newInstance()\n        }\n        fragmentManager.beginTransaction()\n                .replace(R.id.container, fragment, FLEXBOXLAYOUT_FRAGMENT).commit()\n    }\n\n    private fun replaceToRecyclerViewFragment(fragmentManager: FragmentManager) {\n        var fragment: RecyclerViewFragment? = fragmentManager.findFragmentByTag(RECYCLERVIEW_FRAGMENT) as RecyclerViewFragment?\n        if (fragment == null) {\n            fragment = RecyclerViewFragment.newInstance()\n        }\n        fragmentManager.beginTransaction()\n                .replace(R.id.container, fragment, RECYCLERVIEW_FRAGMENT).commit()\n    }\n\n    override fun onNavigationItemSelected(item: MenuItem): Boolean {\n        return false\n    }\n\n    override fun onCreateOptionsMenu(menu: Menu): Boolean {\n        menuInflater.inflate(R.menu.menu_main, menu)\n        return true\n    }\n\n    override fun onOptionsItemSelected(item: MenuItem): Boolean {\n        val id = item.itemId\n\n        if (id == R.id.action_settings) {\n            val intent = Intent(this, SettingsActivity::class.java)\n            startActivity(intent)\n            return true\n        }\n        return super.onOptionsItemSelected(item)\n    }\n\n    companion object {\n\n        private const val FLEXBOXLAYOUT_FRAGMENT = \"flexboxlayout_fragment\"\n\n        private const val RECYCLERVIEW_FRAGMENT = \"recyclerview_fragment\"\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/RecyclerViewFragment.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.os.Bundle\nimport android.view.LayoutInflater\nimport android.view.View\nimport android.view.ViewGroup\nimport androidx.fragment.app.Fragment\nimport androidx.recyclerview.widget.RecyclerView\nimport com.google.android.apps.flexbox.R\nimport com.google.android.material.floatingactionbutton.FloatingActionButton\n\n/**\n * Fragment that contains the [RecyclerView] and the [FlexboxLayoutManager] as its\n * LayoutManager for the flexbox playground.\n */\ninternal class RecyclerViewFragment : Fragment() {\n\n    private lateinit var adapter: FlexItemAdapter\n\n    override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,\n                              savedInstanceState: Bundle?): View? {\n        return inflater.inflate(R.layout.fragment_recyclerview, container, false)\n    }\n\n    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {\n        super.onViewCreated(view, savedInstanceState)\n\n        val recyclerView: RecyclerView = view.findViewById(R.id.recyclerview)\n        val activity = activity as MainActivity\n        val flexboxLayoutManager = FlexboxLayoutManager(activity)\n        recyclerView.layoutManager = flexboxLayoutManager\n        adapter = FlexItemAdapter(activity, flexboxLayoutManager)\n        recyclerView.adapter = adapter\n        if (savedInstanceState != null) {\n            val layoutParams : List<FlexboxLayoutManager.LayoutParams>? = savedInstanceState\n                    .getParcelableArrayList(FLEX_ITEMS_KEY)\n            layoutParams?.let {\n                for (i in layoutParams.indices) {\n                    adapter.addItem(layoutParams[i])\n                }\n            }\n            adapter.notifyDataSetChanged()\n        }\n        val fragmentHelper = FragmentHelper(activity, flexboxLayoutManager)\n        fragmentHelper.initializeViews()\n\n        val addFab: FloatingActionButton = activity.findViewById(R.id.add_fab)\n        addFab.setOnClickListener {\n            val lp = FlexboxLayoutManager.LayoutParams(\n                    ViewGroup.LayoutParams.WRAP_CONTENT,\n                    ViewGroup.LayoutParams.WRAP_CONTENT)\n            fragmentHelper.setFlexItemAttributes(lp)\n            adapter.addItem(lp)\n        }\n        val removeFab: FloatingActionButton = activity.findViewById(R.id.remove_fab)\n        removeFab.setOnClickListener(View.OnClickListener {\n            if (adapter.itemCount == 0) {\n                return@OnClickListener\n            }\n            adapter.removeItem(adapter.itemCount - 1)\n        })\n    }\n\n    override fun onSaveInstanceState(outState: Bundle) {\n        super.onSaveInstanceState(outState)\n        outState.putParcelableArrayList(FLEX_ITEMS_KEY, ArrayList(adapter.items))\n    }\n\n    companion object {\n\n        private const val FLEX_ITEMS_KEY = \"flex_items\"\n\n        fun newInstance(): RecyclerViewFragment {\n            return RecyclerViewFragment()\n        }\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/SettingsActivity.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.os.Bundle\nimport android.widget.Toast\nimport androidx.fragment.app.FragmentActivity\nimport androidx.preference.EditTextPreference\nimport androidx.preference.Preference\nimport androidx.preference.PreferenceFragmentCompat\nimport com.google.android.apps.flexbox.R\nimport com.google.android.flexbox.validators.DimensionInputValidator\nimport com.google.android.flexbox.validators.FlexBasisPercentInputValidator\nimport com.google.android.flexbox.validators.IntegerInputValidator\nimport com.google.android.flexbox.validators.NonNegativeDecimalInputValidator\n\ninternal class SettingsActivity : FragmentActivity() {\n\n    override fun onCreate(savedInstanceState: Bundle?) {\n        super.onCreate(savedInstanceState)\n\n        // Display the fragment as the main content.\n        supportFragmentManager.beginTransaction().replace(android.R.id.content,\n                SettingsFragment()).commit()\n    }\n\n    /**\n     * Fragment for settings.\n     */\n    class SettingsFragment : PreferenceFragmentCompat() {\n\n        override fun onCreatePreferences(savedInstanceState: Bundle?, s: String?) {\n            addPreferencesFromResource(R.xml.new_flex_item_preferences)\n\n            val orderPreference = findPreference(\n                    getString(R.string.new_flex_item_order_key)) as EditTextPreference?\n            orderPreference?.onPreferenceChangeListener = Preference.OnPreferenceChangeListener { _, newValue ->\n                val validator = IntegerInputValidator()\n                if (!validator.isValidInput(newValue.toString())) {\n                    Toast.makeText(activity,\n                            R.string.must_be_integer,\n                            Toast.LENGTH_LONG).show()\n                    return@OnPreferenceChangeListener false\n                }\n                true\n            }\n\n            val flexGrowPreference = findPreference(\n                    getString(R.string.new_flex_grow_key)) as EditTextPreference?\n            flexGrowPreference?.onPreferenceChangeListener = Preference.OnPreferenceChangeListener { _, newValue ->\n                val validator = NonNegativeDecimalInputValidator()\n                if (!validator.isValidInput(newValue.toString())) {\n                    Toast.makeText(activity,\n                            R.string.must_be_non_negative_float,\n                            Toast.LENGTH_LONG).show()\n                    return@OnPreferenceChangeListener false\n                }\n                true\n            }\n\n            val flexShrinkPreference = findPreference(\n                    getString(R.string.new_flex_shrink_key)) as EditTextPreference?\n            flexShrinkPreference?.onPreferenceChangeListener = Preference.OnPreferenceChangeListener { _, newValue ->\n                val validator = NonNegativeDecimalInputValidator()\n                if (!validator.isValidInput(newValue.toString())) {\n                    Toast.makeText(activity,\n                            R.string.must_be_non_negative_float,\n                            Toast.LENGTH_LONG).show()\n                    return@OnPreferenceChangeListener false\n                }\n                true\n            }\n\n            val flexBasisPercentPreference = findPreference(\n                    getString(R.string.new_flex_basis_percent_key)) as EditTextPreference?\n            flexBasisPercentPreference?.onPreferenceChangeListener = Preference.OnPreferenceChangeListener { _, newValue ->\n                val validator = FlexBasisPercentInputValidator()\n                if (!validator.isValidInput(newValue.toString())) {\n                    Toast.makeText(activity,\n                            R.string.must_be_minus_one_or_non_negative_integer,\n                            Toast.LENGTH_LONG).show()\n                    return@OnPreferenceChangeListener false\n                }\n                true\n            }\n\n            val widthPreference = findPreference(\n                    getString(R.string.new_width_key)) as EditTextPreference?\n            widthPreference?.onPreferenceChangeListener = Preference.OnPreferenceChangeListener { _, newValue ->\n                val validator = DimensionInputValidator()\n                if (!validator.isValidInput(newValue.toString())) {\n                    Toast.makeText(activity,\n                            R.string.must_be_minus_one_or_minus_two_or_non_negative_integer,\n                            Toast.LENGTH_LONG).show()\n                    return@OnPreferenceChangeListener false\n                }\n                true\n            }\n\n            val heightPreference = findPreference(\n                    getString(R.string.new_height_key)) as EditTextPreference?\n            heightPreference?.onPreferenceChangeListener = Preference.OnPreferenceChangeListener { _, newValue ->\n                val validator = DimensionInputValidator()\n                if (!validator.isValidInput(newValue.toString())) {\n                    Toast.makeText(activity,\n                            R.string.must_be_minus_one_or_minus_two_or_non_negative_integer,\n                            Toast.LENGTH_LONG).show()\n                    return@OnPreferenceChangeListener false\n                }\n                true\n            }\n        }\n\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/validators/DimensionInputValidator.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.validators\n\nimport android.text.TextUtils\n\n/**\n * Validator for dimension values including match_parent and wrap_content.\n */\nclass DimensionInputValidator : InputValidator {\n\n    override fun isValidInput(charSequence: CharSequence): Boolean {\n        // -1 represents match_parent, -2 represents wrap_content\n        return !charSequence.isEmpty() && (TextUtils.isDigitsOnly(charSequence) ||\n                charSequence.toString() == \"-1\" ||\n                charSequence.toString() == \"-2\")\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/validators/FixedDimensionInputValidator.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.validators\n\nimport android.text.TextUtils\n\n/**\n * Validator for dimension values.\n */\nclass FixedDimensionInputValidator : InputValidator {\n\n    override fun isValidInput(charSequence: CharSequence): Boolean {\n        return !charSequence.isEmpty() && TextUtils.isDigitsOnly(charSequence)\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/validators/FlexBasisPercentInputValidator.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.validators\n\nimport android.text.TextUtils\n\n/**\n * Validator for the flex basis percent attribute.\n */\nclass FlexBasisPercentInputValidator : InputValidator {\n\n    override fun isValidInput(charSequence: CharSequence): Boolean {\n        // -1 represents not set\n        return !charSequence.isEmpty() && (TextUtils.isDigitsOnly(charSequence) || charSequence.toString() == \"-1\")\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/validators/InputValidator.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.validators\n\n/**\n * Interface to verify a given input.\n */\ninterface InputValidator {\n\n    /**\n     * Verifies if the given input is valid.\n\n     * @param charSequence the input to be verified\n     * *\n     * @return `true` if charSequence is valid, `false` otherwise\n     */\n    fun isValidInput(charSequence: CharSequence): Boolean\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/validators/IntegerInputValidator.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.validators\n\n/**\n * Validator for the integers.\n */\nclass IntegerInputValidator : InputValidator {\n\n    override fun isValidInput(charSequence: CharSequence): Boolean {\n        return charSequence.toString().toIntOrNull() != null\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/java/com/google/android/flexbox/validators/NonNegativeDecimalInputValidator.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.validators\n\n/**\n * Validator for non negative integers.\n */\nclass NonNegativeDecimalInputValidator : InputValidator {\n\n    override fun isValidInput(charSequence: CharSequence): Boolean {\n        return charSequence.toString().toFloatOrNull() ?: -1f >= 0\n    }\n}\n"
  },
  {
    "path": "demo-playground/src/main/res/drawable/flex_item_background.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<shape xmlns:android=\"http://schemas.android.com/apk/res/android\" android:shape=\"rectangle\" >\n    <solid android:color=\"@color/lightPink\" />\n    <stroke android:width=\"1dp\" android:color=\"#888888\"/>\n</shape>"
  },
  {
    "path": "demo-playground/src/main/res/drawable/side_nav_bar.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<shape xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:shape=\"rectangle\" >\n    <gradient\n        android:startColor=\"#81C784\"\n        android:centerColor=\"#4CAF50\"\n        android:endColor=\"#2E7D32\"\n        android:type=\"linear\"\n        android:angle=\"135\"/>\n</shape>"
  },
  {
    "path": "demo-playground/src/main/res/layout/activity_main.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<androidx.drawerlayout.widget.DrawerLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:tools=\"http://schemas.android.com/tools\"\n    android:id=\"@+id/drawer_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    android:fitsSystemWindows=\"true\"\n    tools:openDrawer=\"start\">\n\n    <include\n        layout=\"@layout/app_bar_main\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"match_parent\" />\n\n    <com.google.android.material.navigation.NavigationView\n        android:id=\"@+id/nav_view\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"match_parent\"\n        android:layout_gravity=\"start\"\n        android:fitsSystemWindows=\"true\"\n        app:headerLayout=\"@layout/nav_header_main\"\n        app:menu=\"@menu/activity_main_drawer\" />\n\n</androidx.drawerlayout.widget.DrawerLayout>\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/app_bar_main.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:tools=\"http://schemas.android.com/tools\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    android:fitsSystemWindows=\"true\"\n    tools:context=\"com.google.android.flexbox.MainActivity\">\n\n    <com.google.android.material.appbar.AppBarLayout\n        android:layout_height=\"wrap_content\"\n        android:layout_width=\"match_parent\"\n        android:theme=\"@style/AppTheme.AppBarOverlay\">\n\n        <androidx.appcompat.widget.Toolbar\n            android:id=\"@+id/toolbar\"\n            android:layout_width=\"match_parent\"\n            android:layout_height=\"?attr/actionBarSize\"\n            android:background=\"?attr/colorPrimary\"\n            app:popupTheme=\"@style/AppTheme.PopupOverlay\" />\n\n    </com.google.android.material.appbar.AppBarLayout>\n\n    <include layout=\"@layout/content_main\" />\n\n    <com.google.android.material.floatingactionbutton.FloatingActionButton\n        android:id=\"@+id/remove_fab\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:layout_gravity=\"bottom|end\"\n        android:layout_marginRight=\"@dimen/fab_margin\"\n        android:layout_marginEnd=\"@dimen/fab_margin\"\n        android:layout_marginBottom=\"@dimen/second_fab_margin\"\n        android:src=\"@drawable/ic_remove_white_24dp\" />\n\n    <com.google.android.material.floatingactionbutton.FloatingActionButton\n        android:id=\"@+id/add_fab\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:layout_gravity=\"bottom|end\"\n        android:layout_margin=\"@dimen/fab_margin\"\n        android:src=\"@drawable/ic_add_white_24dp\" />\n\n</androidx.coordinatorlayout.widget.CoordinatorLayout>\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/content_main.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<FrameLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/container\"\n    android:layout_height=\"match_parent\"\n    android:layout_width=\"match_parent\"\n    app:layout_behavior=\"@string/appbar_scrolling_view_behavior\" />\n\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/fragment_flex_item_edit.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<ScrollView xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    android:layout_marginEnd=\"@dimen/activity_horizontal_margin\"\n    android:layout_marginStart=\"@dimen/activity_horizontal_margin\"\n    android:layout_marginTop=\"@dimen/activity_vertical_margin\"\n    android:layout_marginBottom=\"@dimen/activity_vertical_margin\">\n\n    <com.google.android.flexbox.FlexboxLayout\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"wrap_content\"\n        android:paddingEnd=\"@dimen/margin_medium\"\n        android:paddingStart=\"@dimen/margin_medium\"\n        app:flexWrap=\"wrap\">\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_order\"\n            android:layout_width=\"100dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_order\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:hint=\"@string/hint_order\"\n                android:inputType=\"numberSigned\"\n                android:lines=\"1\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_flex_grow\"\n            android:layout_width=\"100dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_flex_grow\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:hint=\"@string/hint_flex_grow\"\n                android:inputType=\"numberDecimal\"\n                android:lines=\"1\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_flex_shrink\"\n            android:layout_width=\"100dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_flex_shrink\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:hint=\"@string/hint_flex_shrink\"\n                android:inputType=\"numberDecimal\"\n                android:lines=\"1\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_flex_basis_percent\"\n            android:layout_width=\"200dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_flex_basis_percent\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:hint=\"@string/hint_flex_basis_percent\"\n                android:inputType=\"numberSigned\"\n                android:lines=\"1\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_width\"\n            android:layout_width=\"300dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_wrapBefore=\"true\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_width\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:hint=\"@string/hint_width\"\n                android:inputType=\"numberSigned\"\n                android:lines=\"1\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_height\"\n            android:layout_width=\"300dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_height\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:hint=\"@string/hint_height\"\n                android:inputType=\"numberSigned\"\n                android:lines=\"1\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_min_width\"\n            android:layout_width=\"0dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexBasisPercent=\"22%\"\n            app:layout_minWidth=\"130dp\"\n            app:layout_wrapBefore=\"true\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_min_width\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:lines=\"1\"\n                android:inputType=\"number\"\n                android:hint=\"@string/hint_min_width\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_min_height\"\n            android:layout_width=\"0dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexBasisPercent=\"22%\"\n            app:layout_minWidth=\"130dp\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_min_height\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:lines=\"1\"\n                android:inputType=\"number\"\n                android:hint=\"@string/hint_min_height\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_max_width\"\n            android:layout_width=\"0dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexBasisPercent=\"22%\"\n            app:layout_minWidth=\"130dp\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_max_width\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:lines=\"1\"\n                android:inputType=\"number\"\n                android:hint=\"@string/hint_max_width\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <com.google.android.material.textfield.TextInputLayout\n            android:id=\"@+id/input_layout_max_height\"\n            android:layout_width=\"0dp\"\n            android:layout_height=\"wrap_content\"\n            app:layout_flexBasisPercent=\"22%\"\n            app:layout_minWidth=\"130dp\"\n            app:layout_flexGrow=\"1\">\n\n            <EditText\n                android:id=\"@+id/edit_text_max_height\"\n                android:layout_width=\"match_parent\"\n                android:layout_height=\"wrap_content\"\n                android:lines=\"1\"\n                android:inputType=\"number\"\n                android:hint=\"@string/hint_max_height\"\n                android:maxLines=\"1\" />\n        </com.google.android.material.textfield.TextInputLayout>\n\n        <CheckBox\n            android:id=\"@+id/checkbox_wrap_before\"\n            android:layout_width=\"130dp\"\n            android:layout_height=\"wrap_content\"\n            android:text=\"@string/hint_wrap_before\"\n            app:layout_wrapBefore=\"true\"\n            app:layout_flexGrow=\"1\" />\n\n        <LinearLayout\n            android:layout_width=\"wrap_content\"\n            android:layout_height=\"wrap_content\"\n            android:orientation=\"horizontal\"\n            app:layout_flexGrow=\"1\">\n\n            <TextView\n                android:layout_width=\"wrap_content\"\n                android:layout_height=\"wrap_content\"\n                android:text=\"@string/hint_align_self\" />\n\n            <Spinner\n                android:id=\"@+id/spinner_align_self\"\n                android:layout_width=\"0dp\"\n                android:layout_height=\"wrap_content\"\n                android:layout_weight=\"1\"\n                android:gravity=\"end\" />\n        </LinearLayout>\n\n\n        <LinearLayout\n            android:id=\"@+id/button_panel\"\n            android:layout_width=\"match_parent\"\n            android:layout_height=\"wrap_content\"\n            android:gravity=\"bottom\"\n            android:orientation=\"horizontal\"\n            android:paddingBottom=\"@dimen/margin_small\"\n            android:paddingTop=\"@dimen/margin_small\">\n\n            <View\n                android:id=\"@+id/spacer\"\n                android:layout_width=\"0dp\"\n                android:layout_height=\"0dp\"\n                android:layout_weight=\"1\"\n                android:visibility=\"invisible\" />\n\n            <Button\n                android:id=\"@+id/button_cancel\"\n                style=\"@style/DialogButton\"\n                android:layout_width=\"wrap_content\"\n                android:layout_height=\"wrap_content\"\n                android:text=\"@string/cancel\" />\n\n            <Button\n                android:id=\"@+id/button_ok\"\n                style=\"@style/DialogButton\"\n                android:layout_width=\"wrap_content\"\n                android:layout_height=\"wrap_content\"\n                android:text=\"@string/ok\" />\n        </LinearLayout>\n    </com.google.android.flexbox.FlexboxLayout>\n</ScrollView>\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/fragment_flexboxlayout.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:tools=\"http://schemas.android.com/tools\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:alignContent=\"flex_start\"\n    app:alignItems=\"flex_start\"\n    app:flexWrap=\"wrap\"\n    tools:showIn=\"@layout/activity_main\">\n\n    <TextView\n        android:id=\"@+id/textview1\"\n        style=\"@style/FlexItem\"\n        android:layout_width=\"@dimen/flex_item_length2\"\n        android:layout_height=\"@dimen/flex_item_length\"\n        android:text=\"@string/one\" />\n\n    <TextView\n        android:id=\"@+id/textview2\"\n        style=\"@style/FlexItem\"\n        android:layout_width=\"@dimen/flex_item_length3\"\n        android:layout_height=\"@dimen/flex_item_length\"\n        android:text=\"@string/two\" />\n\n    <TextView\n        android:id=\"@+id/textview3\"\n        style=\"@style/FlexItem\"\n        android:layout_width=\"@dimen/flex_item_length\"\n        android:layout_height=\"@dimen/flex_item_length\"\n        android:text=\"@string/three\" />\n\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "demo-playground/src/main/res/layout/fragment_recyclerview.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<androidx.recyclerview.widget.RecyclerView xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/recyclerview\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\" />\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/nav_header_main.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<LinearLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\"\n    android:background=\"@drawable/side_nav_bar\"\n    android:paddingBottom=\"@dimen/activity_vertical_margin\"\n    android:paddingLeft=\"@dimen/activity_horizontal_margin\"\n    android:paddingRight=\"@dimen/activity_horizontal_margin\"\n    android:paddingTop=\"@dimen/activity_vertical_margin\"\n    android:theme=\"@style/ThemeOverlay.AppCompat.Dark\"\n    android:orientation=\"vertical\"\n    android:gravity=\"bottom\">\n\n    <ImageView\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:paddingTop=\"@dimen/nav_header_vertical_spacing\"\n        android:src=\"@android:drawable/sym_def_app_icon\"\n        android:id=\"@+id/imageView\" />\n\n    <TextView\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"wrap_content\"\n        android:paddingTop=\"@dimen/nav_header_vertical_spacing\"\n        android:text=\"@string/app_name\"\n        android:textAppearance=\"@style/TextAppearance.AppCompat.Body1\" />\n\n    <RadioGroup\n        android:id=\"@+id/radiogroup_container_implementation\"\n        android:checkedButton=\"@+id/radiobutton_viewgroup\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"wrap_content\"\n        android:layout_marginTop=\"@dimen/margin_large\">\n\n        <TextView\n            android:layout_width=\"wrap_content\"\n            android:layout_height=\"wrap_content\"\n            android:text=\"@string/underlying_implementation\" />\n\n        <RadioButton\n            android:id=\"@+id/radiobutton_viewgroup\"\n            android:layout_width=\"wrap_content\"\n            android:layout_height=\"wrap_content\"\n            android:text=\"@string/viewgroup\" />\n\n        <RadioButton\n            android:id=\"@+id/radiobutton_recyclerview\"\n            android:layout_width=\"wrap_content\"\n            android:layout_height=\"wrap_content\"\n            android:text=\"@string/recyclerview\" />\n    </RadioGroup>\n</LinearLayout>\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/spinner_align_content.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<Spinner xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/spinner_align_content\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    android:layout_gravity=\"center_vertical\"\n    android:gravity=\"end\" />\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/spinner_align_items.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<Spinner xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/spinner_align_items\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    android:layout_gravity=\"center_vertical\"\n    android:gravity=\"end\" />\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/spinner_flex_direction.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<Spinner xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/spinner_flex_direction\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    android:layout_gravity=\"center_vertical\"\n    android:gravity=\"end\" />\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/spinner_flex_wrap.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<Spinner xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/spinner_flex_wrap\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    android:layout_gravity=\"center_vertical\"\n    android:gravity=\"end\" />\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/spinner_item.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<TextView xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\"\n    android:textSize=\"13sp\"\n    android:gravity=\"left\"\n    android:textColor=\"@android:color/black\"\n    android:paddingTop=\"@dimen/margin_small\"\n    android:paddingBottom=\"@dimen/margin_small\"\n    android:paddingStart=\"@dimen/margin_tiny\"\n    android:paddingLeft=\"@dimen/margin_tiny\"\n    android:paddingEnd=\"@dimen/margin_tiny\"\n    android:paddingRight=\"@dimen/margin_tiny\" />\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/spinner_justify_content.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<Spinner xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/spinner_justify_content\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    android:layout_gravity=\"center_vertical\"\n    android:gravity=\"end\" />\n"
  },
  {
    "path": "demo-playground/src/main/res/layout/viewholder_flex_item.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<TextView xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/textview\"\n    android:layout_width=\"@dimen/flex_item_length2\"\n    android:layout_height=\"@dimen/flex_item_length\" />\n"
  },
  {
    "path": "demo-playground/src/main/res/menu/activity_main_drawer.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<menu xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\">\n    <group android:checkableBehavior=\"none\">\n        <item\n            android:id=\"@+id/menu_item_flex_direction\"\n            android:title=\"@string/flex_direction\"\n            app:actionLayout=\"@layout/spinner_flex_direction\" />\n        <item\n            android:id=\"@+id/menu_item_flex_wrap\"\n            android:title=\"@string/flex_wrap\"\n            app:actionLayout=\"@layout/spinner_flex_wrap\" />\n        <item\n            android:id=\"@+id/menu_item_justify_content\"\n            android:title=\"@string/justify_content\"\n            app:actionLayout=\"@layout/spinner_justify_content\" />\n        <item\n            android:id=\"@+id/menu_item_align_items\"\n            android:title=\"@string/align_items\"\n            app:actionLayout=\"@layout/spinner_align_items\" />\n        <item\n            android:id=\"@+id/menu_item_align_content\"\n            android:title=\"@string/align_content\"\n            app:actionLayout=\"@layout/spinner_align_content\" />\n    </group>\n</menu>\n"
  },
  {
    "path": "demo-playground/src/main/res/menu/menu_main.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<menu xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:tools=\"http://schemas.android.com/tools\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    tools:context=\"com.google.android.flexbox.MainActivity\">\n    <item\n        android:id=\"@+id/action_settings\"\n        android:title=\"@string/action_settings\"\n        android:orderInCategory=\"100\"\n        app:showAsAction=\"never\" />\n</menu>\n"
  },
  {
    "path": "demo-playground/src/main/res/values/colors.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <color name=\"colorPrimary\">#3F51B5</color>\n    <color name=\"colorPrimaryDark\">#303F9F</color>\n    <color name=\"colorAccent\">#FF4081</color>\n    <color name=\"lightPink\">#FFCEE1</color>\n</resources>\n"
  },
  {
    "path": "demo-playground/src/main/res/values/dimens.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <!-- Default screen margins, per the Android Design guidelines. -->\n    <dimen name=\"nav_header_vertical_spacing\">16dp</dimen>\n    <dimen name=\"nav_header_height\">160dp</dimen>\n\n    <!-- Default screen margins, per the Android Design guidelines. -->\n    <dimen name=\"activity_horizontal_margin\">16dp</dimen>\n    <dimen name=\"activity_vertical_margin\">16dp</dimen>\n    <dimen name=\"fab_margin\">16dp</dimen>\n    <dimen name=\"second_fab_margin\">92dp</dimen>\n\n    <dimen name=\"margin_tiny\">4dp</dimen>\n    <dimen name=\"margin_small\">8dp</dimen>\n    <dimen name=\"margin_medium\">16dp</dimen>\n    <dimen name=\"margin_large\">32dp</dimen>\n    <dimen name=\"margin_huge\">64dp</dimen>\n\n    <dimen name=\"flex_item_length\">80dp</dimen>\n    <dimen name=\"flex_item_length2\">120dp</dimen>\n    <dimen name=\"flex_item_length3\">160dp</dimen>\n</resources>\n"
  },
  {
    "path": "demo-playground/src/main/res/values/strings.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <string name=\"app_name\">Flexbox Playground</string>\n    <string name=\"ok\">OK</string>\n    <string name=\"cancel\">Cancel</string>\n    <string name=\"one\" translatable=\"false\">1</string>\n    <string name=\"two\" translatable=\"false\">2</string>\n    <string name=\"three\" translatable=\"false\">3</string>\n\n    <string name=\"navigation_drawer_open\">Open navigation drawer</string>\n    <string name=\"navigation_drawer_close\">Close navigation drawer</string>\n\n    <string name=\"flex_direction\" translatable=\"false\">Flex Direction</string>\n    <string name=\"flex_wrap\" translatable=\"false\">Flex Wrap</string>\n    <string name=\"justify_content\" translatable=\"false\">Justify Content</string>\n    <string name=\"align_items\" translatable=\"false\">Align Items</string>\n    <string name=\"align_content\" translatable=\"false\">Align Content</string>\n\n    <string name=\"row\" translatable=\"false\">Row</string>\n    <string name=\"row_reverse\" translatable=\"false\">Row Reverse</string>\n    <string name=\"column\" translatable=\"false\">Column</string>\n    <string name=\"column_reverse\" translatable=\"false\">Column Reverse</string>\n    <string name=\"nowrap\" translatable=\"false\">Nowrap</string>\n    <string name=\"wrap\" translatable=\"false\">Wrap</string>\n    <string name=\"wrap_reverse\" translatable=\"false\">Wrap Reverse</string>\n    <string name=\"flex_start\" translatable=\"false\">Flex Start</string>\n    <string name=\"flex_end\" translatable=\"false\">Flex End</string>\n    <string name=\"center\" translatable=\"false\">Center</string>\n    <string name=\"space_between\" translatable=\"false\">Space Between</string>\n    <string name=\"space_around\" translatable=\"false\">Space Around</string>\n    <string name=\"space_evenly\" translatable=\"false\">Space Evenly</string>\n    <string name=\"baseline\" translatable=\"false\">Baseline</string>\n    <string name=\"stretch\" translatable=\"false\">Stretch</string>\n    <string name=\"auto\" translatable=\"false\">Auto</string>\n\n    <string-array translatable=\"false\" name=\"array_flex_direction\">\n        <item>@string/row</item>\n        <item>@string/row_reverse</item>\n        <item>@string/column</item>\n        <item>@string/column_reverse</item>\n    </string-array>\n\n    <string-array translatable=\"false\" name=\"array_flex_wrap\">\n        <item>@string/nowrap</item>\n        <item>@string/wrap</item>\n        <item>@string/wrap_reverse</item>\n    </string-array>\n\n    <string-array translatable=\"false\" name=\"array_justify_content\">\n        <item>@string/flex_start</item>\n        <item>@string/flex_end</item>\n        <item>@string/center</item>\n        <item>@string/space_between</item>\n        <item>@string/space_around</item>\n        <item>@string/space_evenly</item>\n    </string-array>\n\n    <string-array translatable=\"false\" name=\"array_align_items\">\n        <item>@string/flex_start</item>\n        <item>@string/flex_end</item>\n        <item>@string/center</item>\n        <item>@string/baseline</item>\n        <item>@string/stretch</item>\n    </string-array>\n\n    <string-array translatable=\"false\" name=\"array_align_content\">\n        <item>@string/flex_start</item>\n        <item>@string/flex_end</item>\n        <item>@string/center</item>\n        <item>@string/space_between</item>\n        <item>@string/space_around</item>\n        <item>@string/stretch</item>\n    </string-array>\n\n    <string-array translatable=\"false\" name=\"array_align_self\">\n        <item>@string/auto</item>\n        <item>@string/flex_start</item>\n        <item>@string/flex_end</item>\n        <item>@string/center</item>\n        <item>@string/baseline</item>\n        <item>@string/stretch</item>\n    </string-array>\n\n    <string name=\"hint_order\">Order</string>\n    <string name=\"hint_flex_grow\">Flex Grow</string>\n    <string name=\"hint_flex_shrink\">Flex Shrink</string>\n    <string name=\"hint_flex_basis_percent\">Flex Basis Percent (-1: not set)</string>\n    <string name=\"hint_align_self\">Align Self</string>\n    <string name=\"hint_width\">Width (-1: match_parent, -2: wrap_content)</string>\n    <string name=\"hint_height\">Height (-1: match_parent, -2: wrap_content)</string>\n    <string name=\"hint_min_width\">Min Width</string>\n    <string name=\"hint_min_height\">Min Height</string>\n    <string name=\"hint_max_width\">Max Width</string>\n    <string name=\"hint_max_height\">Max Height</string>\n    <string name=\"hint_wrap_before\">Wrap Before</string>\n\n    <string name=\"must_be_non_negative_float\">Must be a non-negative float value</string>\n    <string name=\"must_be_non_negative_integer\">Must be a non-negative integer value</string>\n    <string name=\"must_be_minus_one_or_minus_two_or_non_negative_integer\">Must be -1 or -2 or a non-negative integer value</string>\n    <string name=\"must_be_integer\">Must be an integer value</string>\n    <string name=\"must_be_minus_one_or_non_negative_integer\">Must be -1 or a non-negative integer value</string>\n    <string name=\"invalid_values_exist\">Invalid values exist</string>\n\n    <string name=\"action_settings\">Settings</string>\n    <string name=\"new_flex_items_default\">Default values for new flex items</string>\n    <string name=\"new_flex_items_default_key\" translatable=\"false\">new_flex_items_default_key</string>\n    <string name=\"new_flex_item_order_key\" translatable=\"false\">new_flex_item_order_key</string>\n    <string name=\"new_flex_grow_key\" translatable=\"false\">new_flex_grow_key</string>\n    <string name=\"new_flex_shrink_key\" translatable=\"false\">new_flex_shrink_key</string>\n    <string name=\"new_flex_basis_percent_key\" translatable=\"false\">new_flex_basis_percent_key</string>\n    <string name=\"flex_basis_percent\" translatable=\"false\">Flex Basis Percent</string>\n    <string name=\"flex_basis_percent_summary\">(-1: not set)</string>\n    <string name=\"width\">Width</string>\n    <string name=\"height\">Height</string>\n    <string name=\"size_unit_summary\">(-1: match_parent, -2: wrap_content)</string>\n    <string name=\"new_width_key\" translatable=\"false\">new_width_key</string>\n    <string name=\"new_height_key\" translatable=\"false\">new_height_key</string>\n\n    <string name=\"viewgroup\">ViewGroup</string>\n    <string name=\"recyclerview\">RecyclerView</string>\n    <string name=\"underlying_implementation\">Underlying implementation</string>\n    <string name=\"align_content_not_supported\">Setting the alignContent in FlexboxLayoutManager is not supported. Ignoring.</string>\n    <string name=\"wrap_reverse_not_supported\">wrap_reverse is not supporeted in the FlexboxLayoutManager.</string>\n</resources>\n"
  },
  {
    "path": "demo-playground/src/main/res/values/styles.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n\n    <!-- Base application theme. -->\n    <style name=\"AppThemeBase\" parent=\"Theme.AppCompat.Light.DarkActionBar\">\n        <item name=\"colorPrimary\">@color/colorPrimary</item>\n        <item name=\"colorPrimaryDark\">@color/colorPrimaryDark</item>\n        <item name=\"colorAccent\">@color/colorAccent</item>\n    </style>\n\n    <style name=\"AppTheme\" parent=\"AppThemeBase\">\n        <item name=\"preferenceTheme\">@style/PreferenceThemeOverlay</item>\n    </style>\n\n    <style name=\"AppTheme.NoActionBar\">\n        <item name=\"windowActionBar\">false</item>\n        <item name=\"windowNoTitle\">true</item>\n    </style>\n\n    <style name=\"AppTheme.AppBarOverlay\" parent=\"ThemeOverlay.AppCompat.Dark.ActionBar\" />\n\n    <style name=\"AppTheme.PopupOverlay\" parent=\"ThemeOverlay.AppCompat.Light\" />\n\n    <style name=\"FlexItem\">\n        <item name=\"android:background\">@drawable/flex_item_background</item>\n        <item name=\"android:gravity\">center</item>\n    </style>\n\n    <style name=\"DialogButton\" />\n</resources>\n"
  },
  {
    "path": "demo-playground/src/main/res/values-v14/styles.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n\n    <style name=\"AppTheme\" parent=\"AppThemeBase\">\n        <!--\n            This is needed to make the app work with the preference-v7 library while keeping\n            material theme on API level 14+.\n            See http://stackoverflow.com/questions/32070670/preferencefragmentcompat-requires-preferencetheme-to-be-set\n        -->\n        <item name=\"preferenceTheme\">@style/PreferenceThemeOverlay.v14.Material</item>\n    </style>\n</resources>\n"
  },
  {
    "path": "demo-playground/src/main/res/values-v21/styles.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n\n    <style name=\"AppTheme.NoActionBar\">\n        <item name=\"windowActionBar\">false</item>\n        <item name=\"windowNoTitle\">true</item>\n        <item name=\"android:windowDrawsSystemBarBackgrounds\">true</item>\n        <item name=\"android:statusBarColor\">@android:color/transparent</item>\n    </style>\n\n    <style name=\"DialogButton\" parent=\"@android:style/Widget.Material.Button.Borderless.Colored\" />\n</resources>\n"
  },
  {
    "path": "demo-playground/src/main/res/values-w720dp/dimens.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <!-- Default screen margins, per the Android Design guidelines. -->\n    <dimen name=\"activity_horizontal_margin\">64dp</dimen>\n    <dimen name=\"activity_vertical_margin\">64dp</dimen>\n</resources>\n"
  },
  {
    "path": "demo-playground/src/main/res/xml/new_flex_item_preferences.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<PreferenceScreen xmlns:android=\"http://schemas.android.com/apk/res/android\">\n    <PreferenceCategory\n        android:title=\"@string/new_flex_items_default\"\n        android:key=\"@string/new_flex_items_default_key\">\n        <EditTextPreference\n            android:key=\"@string/new_flex_item_order_key\"\n            android:title=\"@string/hint_order\"\n            android:inputType=\"numberSigned\"\n            android:persistent=\"true\"\n            android:defaultValue=\"1\" />\n\n        <EditTextPreference\n            android:key=\"@string/new_flex_grow_key\"\n            android:title=\"@string/hint_flex_grow\"\n            android:inputType=\"numberDecimal\"\n            android:persistent=\"true\"\n            android:defaultValue=\"0.0\" />\n\n        <EditTextPreference\n            android:key=\"@string/new_flex_shrink_key\"\n            android:title=\"@string/hint_flex_shrink\"\n            android:inputType=\"numberDecimal\"\n            android:persistent=\"true\"\n            android:defaultValue=\"1.0\" />\n\n        <EditTextPreference\n            android:key=\"@string/new_flex_basis_percent_key\"\n            android:title=\"@string/flex_basis_percent\"\n            android:summary=\"@string/flex_basis_percent_summary\"\n            android:inputType=\"numberSigned\"\n            android:persistent=\"true\"\n            android:defaultValue=\"-1\" />\n\n        <EditTextPreference\n            android:key=\"@string/new_width_key\"\n            android:title=\"@string/width\"\n            android:summary=\"@string/size_unit_summary\"\n            android:inputType=\"numberSigned\"\n            android:persistent=\"true\"\n            android:defaultValue=\"120\" />\n\n        <EditTextPreference\n            android:key=\"@string/new_height_key\"\n            android:title=\"@string/height\"\n            android:summary=\"@string/size_unit_summary\"\n            android:inputType=\"numberSigned\"\n            android:persistent=\"true\"\n            android:defaultValue=\"80\" />\n    </PreferenceCategory>\n</PreferenceScreen>"
  },
  {
    "path": "flexbox/.gitignore",
    "content": "/build\n"
  },
  {
    "path": "flexbox/build.gradle",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\napply plugin: 'com.android.library'\napply plugin: 'kotlin-android'\napply from: 'maven-puglisher-plugin.gradle'\n\nandroid {\n    compileSdkVersion rootProject.ext.compileSdkVersion\n\n    defaultConfig {\n        minSdkVersion rootProject.ext.minSdkVersion\n        targetSdkVersion rootProject.ext.targetSdkVersion\n        versionCode 1\n        versionName \"$mavenVersion\"\n\n        testInstrumentationRunner \"androidx.test.runner.AndroidJUnitRunner\"\n\n        consumerProguardFiles 'proguard-rules.txt'\n    }\n    buildTypes {\n        release {\n            minifyEnabled false\n        }\n    }\n\n    libraryVariants.all {\n        it.generateBuildConfigProvider.configure { enabled = false }\n    }\n}\n\ndependencies {\n    compileOnly \"androidx.core:core:${rootProject.androidxCoreVersion}\"\n    compileOnly \"androidx.recyclerview:recyclerview:${rootProject.androidxRecyclerViewVersion}\"\n\n    testImplementation \"junit:junit:${rootProject.junitVersion}\"\n\n    androidTestImplementation \"androidx.core:core:${rootProject.androidxCoreVersion}\"\n    androidTestImplementation \"androidx.recyclerview:recyclerview:${rootProject.androidxRecyclerViewVersion}\"\n    androidTestImplementation \"androidx.annotation:annotation:${rootProject.androidxAnnotationVersion}\"\n    androidTestImplementation \"androidx.test.ext:junit:${rootProject.androidxTestExtVersion}\"\n    androidTestImplementation \"androidx.test:runner:${rootProject.androidxTestVersion}\"\n    androidTestImplementation \"androidx.test:rules:${rootProject.androidxTestVersion}\"\n    androidTestImplementation \"androidx.test.espresso:espresso-core:${rootProject.androidxEspressoVersion}\"\n    androidTestImplementation \"org.jetbrains.kotlin:kotlin-stdlib:${rootProject.kotlinVersion}\"\n}\n"
  },
  {
    "path": "flexbox/constants.gradle",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\next {\n    projectName = 'flexbox-layout'\n    projectDesc = 'Flexbox for Android'\n\n    githubUrl = 'https://github.com/google/flexbox-layout'\n\n    mavenGroup = 'com.google.android.flexbox'\n    mavenArtifactId = 'flexbox'\n    mavenVersion = '3.0.0'\n\n    bintrayOrg = 'google'\n}\n"
  },
  {
    "path": "flexbox/maven-puglisher-plugin.gradle",
    "content": "/*\n * Copyright 2021 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\napply plugin: 'maven-publish'\napply from: 'constants.gradle'\n\nafterEvaluate {\n\n    publishing {\n        publications {\n            release(MavenPublication) {\n                from components.release\n\n                groupId = \"$mavenGroup\"\n                artifactId = \"$mavenArtifactId\"\n                version = \"$mavenVersion\"\n\n                artifact androidSourcesJar\n\n                pom {\n                    name = \"$projectName\"\n                    description = \"$projectDesc\"\n                    licenses {\n                        license {\n                            name = 'The Apache Software License, Version 2.0'\n                            url = 'http://www.apache.org/licenses/LICENSE-2.0.txt'\n                            distribution = 'repo'\n                        }\n                    }\n                    developers {\n                        developer {\n                            name = 'Google'\n                        }\n                    }\n                    scm {\n                        connection = \"${githubUrl}.git\"\n                        url = githubUrl\n                    }\n                }\n            }\n        }\n    }\n}\n\ntask androidSourcesJar(type: Jar) {\n    archiveClassifier.set('sources')\n    from android.sourceSets.main.java.srcDirs\n}"
  },
  {
    "path": "flexbox/proguard-rules.txt",
    "content": "#\n# Copyright 2016 Google Inc. All rights reserved.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n#      http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n#\n\n# The FlexboxLayoutManager may be set from a layout xml, in that situation the RecyclerView\n# tries to instantiate the layout manager using reflection.\n# This is to prevent the layout manager from being obfuscated.\n-keepnames public class com.google.android.flexbox.FlexboxLayoutManager"
  },
  {
    "path": "flexbox/src/androidTest/AndroidManifest.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<manifest\n    package=\"com.google.android.flexbox.test\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\">\n\n    <application>\n        <activity android:name=\".FlexboxTestActivity\"/>\n        <activity android:name=\".ConfigChangeActivity\"\n                  android:configChanges=\"orientation|screenSize|keyboardHidden\"/>\n    </application>\n\n</manifest>\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/FakeFlexContainer.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.view.View\nimport android.view.ViewGroup\n\n/**\n * Fake implementation of [FlexContainer].\n */\ninternal class FakeFlexContainer : FlexContainer {\n\n    private val views = mutableListOf<View>()\n\n    private var flexLines = mutableListOf<FlexLine>()\n\n    @FlexDirection\n    private var flexDirection = FlexDirection.ROW\n\n    @FlexWrap\n    private var flexWrap = FlexWrap.WRAP\n\n    @JustifyContent\n    private var justifyContent = JustifyContent.FLEX_START\n\n    @AlignItems\n    private var alignItems = AlignItems.STRETCH\n\n    @AlignContent\n    private var alignContent = AlignContent.STRETCH\n\n    private var maxLine = -1\n\n    override fun getFlexItemCount() = views.size\n\n    override fun getFlexItemAt(index: Int) = views[index]\n\n    override fun getReorderedFlexItemAt(index: Int) = views[index]\n\n    override fun addView(view: View) {\n        views.add(view)\n    }\n\n    override fun addView(view: View, index: Int) {\n        views.add(index, view)\n    }\n\n    override fun removeAllViews() {\n        views.clear()\n    }\n\n    override fun removeViewAt(index: Int) {\n        views.removeAt(index)\n    }\n\n    override fun getFlexDirection() = flexDirection\n\n    override fun setFlexDirection(@FlexDirection flexDirection: Int) {\n        this.flexDirection = flexDirection\n    }\n\n    override fun getFlexWrap() = flexWrap\n\n    override fun setFlexWrap(@FlexWrap flexWrap: Int) {\n        this.flexWrap = flexWrap\n    }\n\n    override fun getJustifyContent() = justifyContent\n\n    override fun setJustifyContent(@JustifyContent justifyContent: Int) {\n        this.justifyContent = justifyContent\n    }\n\n    override fun getAlignContent() = alignContent\n\n    override fun setAlignContent(@AlignContent alignContent: Int) {\n        this.alignContent = alignContent\n    }\n\n    override fun getAlignItems() = alignItems\n\n    override fun setAlignItems(@AlignItems alignItems: Int) {\n        this.alignItems = alignItems\n    }\n\n    override fun getMaxLine(): Int = this.maxLine\n\n    override fun setMaxLine(maxLine: Int) {\n        this.maxLine = maxLine\n    }\n\n    override fun getFlexLines() = flexLines\n\n    override fun isMainAxisDirectionHorizontal(): Boolean {\n        return flexDirection == FlexDirection.ROW || flexDirection == FlexDirection.ROW_REVERSE\n    }\n\n    override fun getDecorationLengthMainAxis(view: View, index: Int, indexInFlexLine: Int) = 0\n\n    override fun getDecorationLengthCrossAxis(view: View) = 0\n\n    override fun getPaddingTop() = 0\n\n    override fun getPaddingLeft() = 0\n\n    override fun getPaddingRight() = 0\n\n    override fun getPaddingBottom() = 0\n\n    override fun getPaddingStart() = 0\n\n    override fun getPaddingEnd() = 0\n\n    override fun getChildWidthMeasureSpec(widthSpec: Int, padding: Int, childDimension: Int): Int {\n        return ViewGroup.getChildMeasureSpec(widthSpec, padding, childDimension)\n    }\n\n    override fun getChildHeightMeasureSpec(heightSpec: Int, padding: Int, childDimension: Int): Int {\n        return ViewGroup.getChildMeasureSpec(heightSpec, padding, childDimension)\n    }\n\n    override fun getLargestMainSize() = flexLines.maxBy { it.mMainSize }?.mMainSize ?: Integer.MIN_VALUE\n\n    override fun getSumOfCrossSize() = flexLines.sumBy { it.mCrossSize }\n\n    override fun onNewFlexItemAdded(view: View, index: Int, indexInFlexLine: Int, flexLine: FlexLine) = Unit\n\n    override fun onNewFlexLineAdded(flexLine: FlexLine) = Unit\n\n    override fun setFlexLines(flexLines: List<FlexLine>) {\n        this.flexLines = flexLines.toMutableList()\n    }\n\n    override fun getFlexLinesInternal() = flexLines\n\n    override fun updateViewCache(position: Int, view: View) = Unit\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/FlexboxHelperTest.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox\n\nimport android.view.View\nimport android.widget.CheckBox\nimport android.widget.TextView\nimport androidx.core.widget.CompoundButtonCompat\nimport androidx.test.ext.junit.runners.AndroidJUnit4\nimport androidx.test.rule.ActivityTestRule\nimport com.google.android.flexbox.test.FlexboxTestActivity\nimport com.google.android.flexbox.test.IsEqualAllowingError.Companion.isEqualAllowingError\nimport org.hamcrest.Matchers.`is`\nimport org.junit.Assert.assertEquals\nimport org.junit.Assert.assertNotNull\nimport org.junit.Assert.assertThat\nimport org.junit.Before\nimport org.junit.Rule\nimport org.junit.Test\nimport org.junit.runner.RunWith\n\n/**\n * Unit tests for [FlexboxHelper].\n */\n@RunWith(AndroidJUnit4::class)\nclass FlexboxHelperTest {\n\n    private val LONG_TEXT = \"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do \" +\n            \"eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim \" +\n            \"veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo \" +\n            \"consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum \" +\n            \"dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, \" +\n            \"sunt in culpa qui officia deserunt mollit anim id est laborum.\"\n\n    @JvmField\n    @Rule\n    var activityRule = ActivityTestRule(FlexboxTestActivity::class.java)\n\n    private lateinit var flexboxHelper: FlexboxHelper\n\n    private lateinit var flexContainer: FlexContainer\n\n    @Before\n    fun setUp() {\n        flexContainer = FakeFlexContainer()\n        flexboxHelper = FlexboxHelper(flexContainer)\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testCalculateHorizontalFlexLines() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(200, 100)\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(300, 100)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(400, 100)\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.addView(view4)\n        flexContainer.flexWrap = FlexWrap.WRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n\n        flexboxHelper.ensureIndexToFlexLine(flexContainer.flexItemCount)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateHorizontalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n\n        assertEquals(3, result.mFlexLines.size)\n        assertEquals(300, result.mFlexLines[0].mainSize)\n        assertEquals(300, result.mFlexLines[1].mainSize)\n        assertEquals(400, result.mFlexLines[2].mainSize)\n        assertEquals(100, result.mFlexLines[0].crossSize)\n        assertEquals(100, result.mFlexLines[1].crossSize)\n        assertEquals(100, result.mFlexLines[2].crossSize)\n\n        assertNotNull(flexboxHelper.mIndexToFlexLine)\n        assertEquals(0, flexboxHelper.mIndexToFlexLine!![0])\n        assertEquals(0, flexboxHelper.mIndexToFlexLine!![1])\n        assertEquals(1, flexboxHelper.mIndexToFlexLine!![2])\n        assertEquals(2, flexboxHelper.mIndexToFlexLine!![3])\n\n        val firstLine = result.mFlexLines[0]\n        assertEquals(0, firstLine.mFirstIndex)\n        assertEquals(1, firstLine.mLastIndex)\n        val secondLine = result.mFlexLines[1]\n        assertEquals(2, secondLine.mFirstIndex)\n        assertEquals(2, secondLine.mLastIndex)\n        val thirdLine = result.mFlexLines[2]\n        assertEquals(3, thirdLine.mFirstIndex)\n        assertEquals(3, thirdLine.mLastIndex)\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testCalculateVerticalFlexLines() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(100, 200)\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(100, 300)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(100, 400)\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.addView(view4)\n        flexContainer.flexWrap = FlexWrap.WRAP\n        flexContainer.flexDirection = FlexDirection.COLUMN\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n\n        flexboxHelper.ensureIndexToFlexLine(flexContainer.flexItemCount)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateVerticalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n\n        assertEquals(3, result.mFlexLines.size)\n        assertEquals(300, result.mFlexLines[0].mainSize)\n        assertEquals(300, result.mFlexLines[1].mainSize)\n        assertEquals(400, result.mFlexLines[2].mainSize)\n        assertEquals(100, result.mFlexLines[0].crossSize)\n        assertEquals(100, result.mFlexLines[1].crossSize)\n        assertEquals(100, result.mFlexLines[2].crossSize)\n\n        assertNotNull(flexboxHelper.mIndexToFlexLine)\n        assertEquals(0, flexboxHelper.mIndexToFlexLine!![0])\n        assertEquals(0, flexboxHelper.mIndexToFlexLine!![1])\n        assertEquals(1, flexboxHelper.mIndexToFlexLine!![2])\n        assertEquals(2, flexboxHelper.mIndexToFlexLine!![3])\n\n        val firstLine = result.mFlexLines[0]\n        assertEquals(0, firstLine.mFirstIndex)\n        assertEquals(1, firstLine.mLastIndex)\n        val secondLine = result.mFlexLines[1]\n        assertEquals(2, secondLine.mFirstIndex)\n        assertEquals(2, secondLine.mLastIndex)\n        val thirdLine = result.mFlexLines[2]\n        assertEquals(3, thirdLine.mFirstIndex)\n        assertEquals(3, thirdLine.mLastIndex)\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineMainSize_direction_row_flexGrowSet() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(200, 100)\n        lp2.flexGrow = 1.0f\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(300, 100)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(400, 100)\n        lp4.flexGrow = 2.0f\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.addView(view4)\n        flexContainer.flexDirection = FlexDirection.ROW\n        flexContainer.flexWrap = FlexWrap.WRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateHorizontalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n\n        assertThat(view1.measuredWidth, `is`(100))\n        assertThat(view1.measuredHeight, `is`(100))\n        // view2 will expand to fill the left space in the first flex line since flex grow is set\n        assertThat(view2.measuredWidth, `is`(400))\n        assertThat(view2.measuredHeight, `is`(100))\n        assertThat(view3.measuredWidth, `is`(300))\n        assertThat(view3.measuredHeight, `is`(100))\n        // view4 will expand to fill the left space in the first flex line since flex grow is set\n        assertThat(view4.measuredWidth, `is`(500))\n        assertThat(view4.measuredHeight, `is`(100))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineMainSize_direction_column_flexGrowSet() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(100, 200)\n        lp2.flexGrow = 1.0f\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(100, 300)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(100, 400)\n        lp4.flexGrow = 2.0f\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.addView(view4)\n        flexContainer.flexDirection = FlexDirection.COLUMN\n        flexContainer.flexWrap = FlexWrap.WRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateVerticalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n\n        assertThat(view1.measuredWidth, `is`(100))\n        assertThat(view1.measuredHeight, `is`(100))\n        assertThat(view2.measuredWidth, `is`(100))\n        // view2 will expand to fill the left space in the first flex line since flex grow is set\n        assertThat(view2.measuredHeight, `is`(400))\n        assertThat(view3.measuredWidth, `is`(100))\n        assertThat(view3.measuredHeight, `is`(300))\n        assertThat(view4.measuredWidth, `is`(100))\n        // view4 will expand to fill the left space in the first flex line since flex grow is set\n        assertThat(view4.measuredHeight, `is`(500))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineMainSize_direction_row_flexShrinkSet() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(200, 100)\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(200, 100)\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(200, 100)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(200, 100)\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.addView(view4)\n        flexContainer.flexDirection = FlexDirection.ROW\n        flexContainer.flexWrap = FlexWrap.NOWRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateVerticalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n\n        // Flex shrink is set to 1.0 (default value) for all views.\n        // They should be shrank equally for the amount overflown the width\n        assertThat(view1.measuredWidth, `is`(125))\n        assertThat(view1.measuredHeight, `is`(100))\n        assertThat(view2.measuredWidth, `is`(125))\n        assertThat(view2.measuredHeight, `is`(100))\n        assertThat(view3.measuredWidth, `is`(125))\n        assertThat(view3.measuredHeight, `is`(100))\n        assertThat(view4.measuredWidth, `is`(125))\n        assertThat(view4.measuredHeight, `is`(100))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineMainSize_direction_column_flexShrinkSet() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 200)\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(100, 200)\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(100, 200)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(100, 200)\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.addView(view4)\n        flexContainer.flexDirection = FlexDirection.COLUMN\n        flexContainer.flexWrap = FlexWrap.NOWRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateVerticalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n\n        // Flex shrink is set to 1.0 (default value) for all views.\n        // They should be shrank equally for the amount overflown the height\n        assertThat(view1.measuredWidth, `is`(100))\n        assertThat(view1.measuredHeight, `is`(125))\n        assertThat(view2.measuredWidth, `is`(100))\n        assertThat(view2.measuredHeight, `is`(125))\n        assertThat(view3.measuredWidth, `is`(100))\n        assertThat(view3.measuredHeight, `is`(125))\n        assertThat(view4.measuredWidth, `is`(100))\n        assertThat(view4.measuredHeight, `is`(125))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineMainSize_directionRow_fixedSizeViewAndShrinkable_doNotExceedMaxMainSize() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n        val view1 = View(activity)\n        lp1.flexShrink = 0f\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(\n                FlexboxLayout.LayoutParams.WRAP_CONTENT,\n                FlexboxLayout.LayoutParams.WRAP_CONTENT)\n        val view2 = TextView(activity)\n        view2.layoutParams = lp2\n        view2.text = LONG_TEXT\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.flexWrap = FlexWrap.NOWRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.AT_MOST)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateHorizontalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n\n        // Container with WRAP_CONTENT and a max width forces resizable children to shrink\n        // to avoid exceeding max available space.\n        assertThat(view1.measuredWidth, `is`(100))\n        assertThat(view2.measuredWidth, `is`(400))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineMainSize_directionRow_twoFixedSizeViewsAndShrinkable_doNotExceedMaxMainSize() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n        val view1 = View(activity)\n        lp1.flexShrink = 0f\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(\n                FlexboxLayout.LayoutParams.WRAP_CONTENT,\n                FlexboxLayout.LayoutParams.WRAP_CONTENT)\n        val view2 = TextView(activity)\n        view2.layoutParams = lp2\n        view2.text = LONG_TEXT\n        val lp3 = FlexboxLayout.LayoutParams(100, 100)\n        val view3 = View(activity)\n        lp3.flexShrink = 0f\n        view3.layoutParams = lp3\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.flexWrap = FlexWrap.NOWRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.AT_MOST)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateHorizontalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n\n        // Container with WRAP_CONTENT and a max width forces resizable children to shrink\n        // to avoid exceeding max available space.\n        assertThat(view1.measuredWidth, `is`(100))\n        assertThat(view2.measuredWidth, `is`(300))\n        assertThat(view3.measuredWidth, `is`(100))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineMainSize_directionRow_considerCompoundButtonImplicitMinSizeWhenNotSpecified() {\n        val containerWidth = 500\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(\n                FlexboxLayout.LayoutParams.WRAP_CONTENT,\n                FlexboxLayout.LayoutParams.WRAP_CONTENT)\n        val view1 = CheckBox(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(\n                FlexboxLayout.LayoutParams.WRAP_CONTENT,\n                FlexboxLayout.LayoutParams.WRAP_CONTENT)\n        val view2 = TextView(activity)\n        view2.layoutParams = lp2\n        view2.text = LONG_TEXT\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.flexWrap = FlexWrap.NOWRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(containerWidth, View.MeasureSpec.AT_MOST)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateHorizontalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n\n        // CompoundButton will use its ButtonDrawable minWidth to determine its size when\n        // no minimum width is set on it.\n        val drawableMinWidth = CompoundButtonCompat.getButtonDrawable(view1)!!.minimumWidth\n        val expectedTextWidth = containerWidth - drawableMinWidth\n        assertThat(view1.measuredWidth, `is`(drawableMinWidth))\n        assertThat(view2.measuredWidth, `is`(expectedTextWidth))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineMainSize_directionRow_considerCompoundButtonExplicitMinSizeWhenSpecified() {\n        val containerWidth = 500\n        val compoundButtonMinWidth = 150\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(\n                FlexboxLayout.LayoutParams.WRAP_CONTENT,\n                FlexboxLayout.LayoutParams.WRAP_CONTENT)\n        lp1.minWidth = compoundButtonMinWidth\n        val view1 = CheckBox(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(\n                FlexboxLayout.LayoutParams.WRAP_CONTENT,\n                FlexboxLayout.LayoutParams.WRAP_CONTENT)\n        val view2 = TextView(activity)\n        view2.layoutParams = lp2\n        view2.text = LONG_TEXT\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.flexWrap = FlexWrap.NOWRAP\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(containerWidth, View.MeasureSpec.AT_MOST)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.UNSPECIFIED)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateHorizontalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n\n        // CompoundButton will be measured based on its explicitly specified minWidth.\n        val expectedTextWidth = containerWidth - compoundButtonMinWidth\n        assertThat(view1.measuredWidth, `is`(compoundButtonMinWidth))\n        assertThat(view2.measuredWidth, `is`(expectedTextWidth))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineCrossSize_direction_row_alignContent_stretch() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(200, 100)\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(300, 100)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(400, 100)\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.addView(view4)\n        flexContainer.flexDirection = FlexDirection.ROW\n        flexContainer.flexWrap = FlexWrap.WRAP\n        flexContainer.alignContent = AlignContent.STRETCH\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.EXACTLY)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateHorizontalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n        flexboxHelper.determineCrossSize(widthMeasureSpec, heightMeasureSpec, 0)\n        flexboxHelper.stretchViews()\n\n        // align content is set to Align.STRETCH, the cross size for each flex line is stretched\n        // to distribute the remaining free space along the cross axis\n        // (remaining height in this case)\n        assertThat(view1.measuredHeight, isEqualAllowingError(333))\n        assertThat(view2.measuredHeight, isEqualAllowingError(333))\n        assertThat(view3.measuredHeight, isEqualAllowingError(333))\n        assertThat(view4.measuredHeight, isEqualAllowingError(333))\n    }\n\n    @Test\n    @Throws(Throwable::class)\n    fun testDetermineCrossSize_direction_column_alignContent_stretch() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(100, 200)\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(100, 300)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(100, 400)\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.addView(view1)\n        flexContainer.addView(view2)\n        flexContainer.addView(view3)\n        flexContainer.addView(view4)\n        flexContainer.flexDirection = FlexDirection.COLUMN\n        flexContainer.flexWrap = FlexWrap.WRAP\n        flexContainer.alignContent = AlignContent.STRETCH\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.EXACTLY)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateVerticalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        flexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec)\n        flexboxHelper.determineCrossSize(widthMeasureSpec, heightMeasureSpec, 0)\n        flexboxHelper.stretchViews()\n\n        // align content is set to Align.STRETCH, the cross size for each flex line is stretched\n        // to distribute the remaining free space along the cross axis\n        // (remaining width in this case)\n        assertThat(view1.measuredWidth, isEqualAllowingError(333))\n        assertThat(view2.measuredWidth, isEqualAllowingError(333))\n        assertThat(view3.measuredWidth, isEqualAllowingError(333))\n        assertThat(view4.measuredWidth, isEqualAllowingError(333))\n    }\n\n    @Test\n    fun testMakeCombinedLong() {\n        var higher = -1\n        var lower = 10\n        var combined = flexboxHelper.makeCombinedLong(lower, higher)\n        assertThat(flexboxHelper.extractHigherInt(combined), `is`(higher))\n        assertThat(flexboxHelper.extractLowerInt(combined), `is`(lower))\n\n        higher = Integer.MAX_VALUE\n        lower = Integer.MIN_VALUE\n        combined = flexboxHelper.makeCombinedLong(lower, higher)\n        assertThat(flexboxHelper.extractHigherInt(combined), `is`(higher))\n        assertThat(flexboxHelper.extractLowerInt(combined), `is`(lower))\n\n        higher = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        lower = View.MeasureSpec.makeMeasureSpec(300, View.MeasureSpec.UNSPECIFIED)\n        combined = flexboxHelper.makeCombinedLong(lower, higher)\n        assertThat(flexboxHelper.extractHigherInt(combined), `is`(higher))\n        assertThat(flexboxHelper.extractLowerInt(combined), `is`(lower))\n    }\n\n    @Test\n    fun testFlexLine_anyItemsHaveFlexGrow() {\n        val activity = activityRule.activity\n        val lp1 = FlexboxLayout.LayoutParams(100, 100).apply {\n            flexGrow = 1.0f\n        }\n        val view1 = View(activity)\n        view1.layoutParams = lp1\n        val lp2 = FlexboxLayout.LayoutParams(100, 200)\n        val view2 = View(activity)\n        view2.layoutParams = lp2\n        val lp3 = FlexboxLayout.LayoutParams(100, 300)\n        val view3 = View(activity)\n        view3.layoutParams = lp3\n        val lp4 = FlexboxLayout.LayoutParams(100, 400).apply {\n            flexGrow = 2.0f\n        }\n        val view4 = View(activity)\n        view4.layoutParams = lp4\n        flexContainer.apply {\n            addView(view1)\n            addView(view2)\n            addView(view3)\n            addView(view4)\n            flexDirection = FlexDirection.COLUMN\n            flexWrap = FlexWrap.WRAP\n            alignContent = AlignContent.STRETCH\n        }\n        val widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(1000, View.MeasureSpec.EXACTLY)\n        val heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(500, View.MeasureSpec.EXACTLY)\n        val result = FlexboxHelper.FlexLinesResult()\n        flexboxHelper.calculateVerticalFlexLines(result, widthMeasureSpec, heightMeasureSpec)\n        flexContainer.flexLines = result.mFlexLines\n        assertThat(flexContainer.flexLines.size, `is`(3))\n        assertThat(flexContainer.flexLines[0].mAnyItemsHaveFlexGrow, `is`(true))\n        assertThat(flexContainer.flexLines[1].mAnyItemsHaveFlexGrow, `is`(false))\n        assertThat(flexContainer.flexLines[2].mAnyItemsHaveFlexGrow, `is`(true))\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/ConfigChangeActivity.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.app.Activity\nimport android.content.res.Configuration\nimport android.util.Log\n\nimport com.google.android.flexbox.FlexboxLayout\n\n/**\n * Activity for testing the [FlexboxLayout] that handles configuration changes by itself\n * instead of letting the system take care of those.\n */\nclass ConfigChangeActivity : Activity() {\n    override fun onConfigurationChanged(newConfig: Configuration) {\n        super.onConfigurationChanged(newConfig)\n\n        Log.d(TAG, \"onConfigurationChanged: $newConfig\")\n    }\n\n    companion object {\n        private const val TAG = \"ConfigChangeActivity\"\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/FlexboxAndroidTest.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.content.Context\nimport android.view.View\nimport android.view.ViewGroup\nimport android.widget.TextView\nimport androidx.annotation.LayoutRes\nimport androidx.core.content.res.ResourcesCompat\nimport androidx.test.espresso.Espresso.onView\nimport androidx.test.espresso.ViewAssertion\nimport androidx.test.espresso.assertion.PositionAssertions.isBottomAlignedWith\nimport androidx.test.espresso.assertion.PositionAssertions.isCompletelyAbove\nimport androidx.test.espresso.assertion.PositionAssertions.isCompletelyBelow\nimport androidx.test.espresso.assertion.PositionAssertions.isCompletelyLeftOf\nimport androidx.test.espresso.assertion.PositionAssertions.isCompletelyRightOf\nimport androidx.test.espresso.assertion.PositionAssertions.isLeftAlignedWith\nimport androidx.test.espresso.assertion.PositionAssertions.isRightAlignedWith\nimport androidx.test.espresso.assertion.PositionAssertions.isTopAlignedWith\nimport androidx.test.espresso.assertion.ViewAssertions.matches\nimport androidx.test.espresso.matcher.ViewMatchers.withId\nimport androidx.test.ext.junit.runners.AndroidJUnit4\nimport androidx.test.filters.FlakyTest\nimport androidx.test.filters.MediumTest\nimport androidx.test.platform.app.InstrumentationRegistry\nimport androidx.test.rule.ActivityTestRule\nimport com.google.android.flexbox.AlignContent\nimport com.google.android.flexbox.AlignItems\nimport com.google.android.flexbox.FlexDirection\nimport com.google.android.flexbox.FlexWrap\nimport com.google.android.flexbox.FlexboxLayout\nimport com.google.android.flexbox.JustifyContent\nimport com.google.android.flexbox.test.IsEqualAllowingError.Companion.isEqualAllowingError\nimport org.hamcrest.Description\nimport org.hamcrest.TypeSafeMatcher\nimport org.hamcrest.core.Is.`is`\nimport org.hamcrest.core.IsNot.not\nimport org.junit.Assert.assertEquals\nimport org.junit.Assert.assertNotNull\nimport org.junit.Assert.assertThat\nimport org.junit.Assert.assertTrue\nimport org.junit.Rule\nimport org.junit.Test\nimport org.junit.runner.RunWith\n\n/**\n * Integration tests for [FlexboxLayout].\n */\n@RunWith(AndroidJUnit4::class)\n@MediumTest\nclass FlexboxAndroidTest {\n\n    @JvmField\n    @Rule\n    var activityRule = ActivityTestRule(FlexboxTestActivity::class.java)\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testLoadFromLayoutXml() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_simple)\n\n        assertNotNull(flexboxLayout)\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.CENTER))\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.CENTER))\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.CENTER))\n        assertThat(flexboxLayout.childCount, `is`(1))\n\n        val child = flexboxLayout.getChildAt(0)\n        val lp = child.layoutParams as FlexboxLayout.LayoutParams\n        assertThat(lp.order, `is`(2))\n        assertThat(lp.flexGrow, `is`(1f))\n        assertThat(lp.alignSelf, `is`(AlignItems.STRETCH))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testOrderAttribute_fromLayoutXml() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_order_test)\n\n        assertNotNull(flexboxLayout)\n        assertThat(flexboxLayout.childCount, `is`(4))\n        // order: -1, index 1\n        assertThat((flexboxLayout.getReorderedChildAt(0) as TextView).text.toString(), `is`(\"2\"))\n        // order: 0, index 2\n        assertThat((flexboxLayout.getReorderedChildAt(1) as TextView).text.toString(), `is`(\"3\"))\n        // order: 1, index 3\n        assertThat((flexboxLayout.getReorderedChildAt(2) as TextView).text.toString(), `is`(\"4\"))\n        // order: 2, index 0\n        assertThat((flexboxLayout.getReorderedChildAt(3) as TextView).text.toString(), `is`(\"1\"))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testOrderAttribute_fromCode() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_order_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val fifth = createTextView(activity, \"5\", 0)\n                        val sixth = createTextView(activity, \"6\", -10)\n                        flexboxLayout.addView(fifth)\n                        flexboxLayout.addView(sixth)\n                    }\n                })\n\n        assertThat(flexboxLayout.childCount, `is`(6))\n        // order: -10, index 5\n        assertThat((flexboxLayout.getReorderedChildAt(0) as TextView).text.toString(), `is`(\"6\"))\n        // order: -1, index 1\n        assertThat((flexboxLayout.getReorderedChildAt(1) as TextView).text.toString(), `is`(\"2\"))\n        // order: 0, index 2\n        assertThat((flexboxLayout.getReorderedChildAt(2) as TextView).text.toString(), `is`(\"3\"))\n        // order: 0, index 4\n        assertThat((flexboxLayout.getReorderedChildAt(3) as TextView).text.toString(), `is`(\"5\"))\n        // order: 1, index 3\n        assertThat((flexboxLayout.getReorderedChildAt(4) as TextView).text.toString(), `is`(\"4\"))\n        // order: 2, index 0\n        assertThat((flexboxLayout.getReorderedChildAt(5) as TextView).text.toString(), `is`(\"1\"))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChangeOrder_fromChildSetLayoutParams() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_order_test)\n\n        assertThat(flexboxLayout.childCount, `is`(4))\n        // order: -1, index 1\n        assertThat((flexboxLayout.getReorderedChildAt(0) as TextView).text.toString(), `is`(\"2\"))\n        // order: 0, index 2\n        assertThat((flexboxLayout.getReorderedChildAt(1) as TextView).text.toString(), `is`(\"3\"))\n        // order: 0, index 3\n        assertThat((flexboxLayout.getReorderedChildAt(2) as TextView).text.toString(), `is`(\"4\"))\n        // order: 2, index 0\n        assertThat((flexboxLayout.getReorderedChildAt(3) as TextView).text.toString(), `is`(\"1\"))\n\n        // By changing the order and calling the setLayoutParams, the reordered array in the\n        // FlexboxLayout (mReorderedIndices) will be recreated without adding a new View.\n        activityRule.runOnUiThread {\n            val view1 = flexboxLayout.getChildAt(0)\n            val lp = view1.layoutParams as FlexboxLayout.LayoutParams\n            lp.order = -3\n            view1.layoutParams = lp\n        }\n        // order: -3, index 0\n        assertThat((flexboxLayout.getReorderedChildAt(3) as TextView).text.toString(), `is`(\"1\"))\n        // order: -1, index 1\n        assertThat((flexboxLayout.getReorderedChildAt(0) as TextView).text.toString(), `is`(\"2\"))\n        // order: 0, index 2\n        assertThat((flexboxLayout.getReorderedChildAt(1) as TextView).text.toString(), `is`(\"3\"))\n        // order: 1, index 3\n        assertThat((flexboxLayout.getReorderedChildAt(2) as TextView).text.toString(), `is`(\"4\"))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testOrderAttribute_addViewInMiddle() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_order_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val fifth = createTextView(activity, \"5\", 0)\n                        // Add the new TextView in the middle of the indices\n                        flexboxLayout.addView(fifth, 2)\n                    }\n                })\n\n        assertNotNull(flexboxLayout)\n        assertThat(flexboxLayout.childCount, `is`(5))\n        // order: -1, index 1\n        assertThat((flexboxLayout.getReorderedChildAt(0) as TextView).text.toString(), `is`(\"2\"))\n        // order: 0, index 2\n        assertThat((flexboxLayout.getReorderedChildAt(1) as TextView).text.toString(), `is`(\"5\"))\n        // order: 0, index 3\n        assertThat((flexboxLayout.getReorderedChildAt(2) as TextView).text.toString(), `is`(\"3\"))\n        // order: 0, index 4\n        assertThat((flexboxLayout.getReorderedChildAt(3) as TextView).text.toString(), `is`(\"4\"))\n        // order: 2, index 0\n        assertThat((flexboxLayout.getReorderedChildAt(4) as TextView).text.toString(), `is`(\"1\"))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testOrderAttribute_removeLastView() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_order_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.removeViewAt(flexboxLayout.childCount - 1)\n                    }\n                })\n\n        assertNotNull(flexboxLayout)\n        assertThat(flexboxLayout.childCount, `is`(3))\n        // order: -1, index 1\n        assertThat((flexboxLayout.getReorderedChildAt(0) as TextView).text.toString(), `is`(\"2\"))\n        // order: 0, index 2\n        assertThat((flexboxLayout.getReorderedChildAt(1) as TextView).text.toString(), `is`(\"3\"))\n        // order: 2, index 0\n        assertThat((flexboxLayout.getReorderedChildAt(2) as TextView).text.toString(), `is`(\"1\"))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testOrderAttribute_removeViewInMiddle() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_order_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.removeViewAt(2)\n                    }\n                })\n\n        assertNotNull(flexboxLayout)\n        assertThat(flexboxLayout.childCount, `is`(3))\n        // order: -1, index 1\n        assertThat((flexboxLayout.getReorderedChildAt(0) as TextView).text.toString(), `is`(\"2\"))\n        // order: 0, index 3\n        assertThat((flexboxLayout.getReorderedChildAt(1) as TextView).text.toString(), `is`(\"4\"))\n        // order: 2, index 0\n        assertThat((flexboxLayout.getReorderedChildAt(2) as TextView).text.toString(), `is`(\"1\"))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexWrap_wrap() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_wrap_test)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        // The width of the FlexboxLayout is not enough for placing the three text views.\n        // The third text view should be placed below the first one\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        val activity = activityRule.activity\n        assertThat(flexLine1.mainSize, `is`(activity.dpToPixel(320)))\n        assertThat(flexLine1.crossSize, `is`(activity.dpToPixel(120)))\n        val flexLine2 = flexLines[1]\n        assertThat(flexLine2.mainSize, `is`(activity.dpToPixel(160)))\n        assertThat(flexLine2.crossSize, `is`(activity.dpToPixel(120)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexWrap_nowrap() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_wrap_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.NOWRAP\n                        flexboxLayout.alignItems = AlignItems.FLEX_START\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.NOWRAP))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        // The width of the FlexboxLayout is not enough for placing the three text views.\n        // But the flexWrap attribute is set to NOWRAP, the third text view is placed\n        // to the right of the second one and overflowing the parent FlexboxLayout.\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        assertThat(flexboxLayout.flexLines.size, `is`(1))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(1))\n        val flexLine = flexLines[0]\n        val activity = activityRule.activity\n        assertThat(flexLine.mainSize, `is`(activity.dpToPixel(480)))\n        assertThat(flexLine.crossSize, `is`(activity.dpToPixel(300)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexWrap_wrap_reverse() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_wrap_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP_REVERSE))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        // The width of the FlexboxLayout is not enough for placing the three text views.\n        // There should be two flex lines same as WRAP, but the layout starts from bottom\n        // to top in FlexWrap.WRAP_REVERSE\n        onView(withId(R.id.text3)).check(isCompletelyAbove(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyAbove(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        assertThat(flexboxLayout.flexLines.size, `is`(2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexWrap_wrap_flexDirection_column() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_wrap_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        // The height of the FlexboxLayout is not enough for placing the three text views.\n        // The third text view should be placed right of the first one\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        assertThat(flexboxLayout.flexLines.size, `is`(2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexWrap_nowrap_flexDirection_column() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_wrap_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.flexWrap = FlexWrap.NOWRAP\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.NOWRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        // The height of the FlexboxLayout is not enough for placing the three text views.\n        // But the flexWrap attribute is set to NOWRAP, the third text view is placed\n        // below the second one and overflowing the parent FlexboxLayout.\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        assertThat(flexboxLayout.flexLines.size, `is`(1))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexWrap_wrap_reverse_flexDirection_column() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_wrap_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP_REVERSE))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        // The width of the FlexboxLayout is not enough for placing the three text views.\n        // There should be two flex lines same as WRAP, but the layout starts from right\n        // to left in FlexWrap.WRAP_REVERSE\n        onView(withId(R.id.text3)).check(isCompletelyLeftOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyLeftOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        assertThat(flexboxLayout.flexLines.size, `is`(2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexItem_match_parent() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_item_match_parent)\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n\n        assertThat(text1.width, `is`(flexboxLayout.width))\n        assertThat(text2.width, `is`(flexboxLayout.width))\n        assertThat(text3.width, `is`(flexboxLayout.width))\n        assertThat(flexboxLayout.height, `is`(text1.height + text2.height + text3.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexItem_match_parent_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_flex_item_match_parent_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n\n        assertThat(text1.height, `is`(flexboxLayout.height))\n        assertThat(text2.height, `is`(flexboxLayout.height))\n        assertThat(text3.height, `is`(flexboxLayout.height))\n        assertThat(flexboxLayout.width, `is`(text1.width + text2.width + text3.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexboxLayout_wrapContent() {\n        createFlexboxLayout(R.layout.activity_flexbox_wrap_content)\n        // The parent FlexboxLayout's layout_width and layout_height are set to wrap_content\n        // The size of the FlexboxLayout is aligned with three text views.\n\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexboxLayout_wrapped_with_ScrollView() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flexbox_wrapped_with_scrollview)\n\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n\n        // The heightMode of the FlexboxLayout is set as MeasureSpec.UNSPECIFIED, the height of the\n        // layout will be expanded to include the all children views\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(flexboxLayout.height, `is`(textView1.height + textView3.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexboxLayout_wrapped_with_HorizontalScrollView() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_flexbox_wrapped_with_horizontalscrollview)\n\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        // The widthMode of the FlexboxLayout is set as MeasureSpec.UNSPECIFIED, the width of the\n        // layout will be expanded to include the all children views\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(flexboxLayout.width, `is`(textView1.width + textView2.width + textView3.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexStart() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test)\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.FLEX_START))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexStart_withParentPadding() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_justify_content_with_parent_padding)\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.FLEX_START))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        // Both the parent FrameLayout and the FlexboxLayout have different padding values\n        // but the text1.getLeft should be the padding value for the FlexboxLayout, not including\n        // the parent's padding value\n        assertThat(text1.left, `is`(flexboxLayout.paddingLeft))\n        assertThat(text1.top, `is`(flexboxLayout.paddingTop))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexEnd() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.FLEX_END\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.FLEX_END))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyLeftOf(withId(R.id.text3)))\n        onView(withId(R.id.text1)).check(isCompletelyLeftOf(withId(R.id.text2)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexEnd_withParentPadding() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_justify_content_with_parent_padding,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.FLEX_END\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.FLEX_END))\n        onView(withId(R.id.text2)).check(isCompletelyLeftOf(withId(R.id.text3)))\n        onView(withId(R.id.text1)).check(isCompletelyLeftOf(withId(R.id.text2)))\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        // Both the parent FrameLayout and the FlexboxLayout have different padding values\n        // but the text3.getRight should be the padding value for the FlexboxLayout, not including\n        // the parent's padding value\n        assertThat(flexboxLayout.width - text3.right, `is`(flexboxLayout.paddingRight))\n        assertThat(text3.top, `is`(flexboxLayout.paddingTop))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_center() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.CENTER\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.CENTER))\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val space = (flexboxLayout.width - textView1.width - textView2.width - textView3.width) / 2\n        assertThat(textView1.left, isEqualAllowingError(space))\n        assertThat(flexboxLayout.right - textView3.right, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_center_withParentPadding() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_justify_content_with_parent_padding,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.CENTER\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.CENTER))\n\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.width - textView1.width - textView2.width -\n                textView3.width - flexboxLayout.paddingLeft - flexboxLayout.paddingRight\n        space /= 2\n        assertThat(textView1.left - flexboxLayout.paddingLeft, isEqualAllowingError(space))\n        assertThat(flexboxLayout.width - textView3.right - flexboxLayout.paddingRight,\n                isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_BETWEEN\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.width - textView1.width - textView2.width - textView3.width\n        space /= 2\n        assertThat(textView2.left - textView1.right, isEqualAllowingError(space))\n        assertThat(textView3.left - textView2.right, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_withPadding() {\n        val activity = activityRule.activity\n        val padding = 40\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_BETWEEN\n                        flexboxLayout.setPadding(padding, padding, padding, padding)\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.width - textView1.width - textView2.width - textView3.width -\n                padding * 2\n        space /= 2\n        assertThat(textView1.left, `is`(padding))\n        assertThat(flexboxLayout.right - textView3.right, `is`(padding))\n        assertThat(textView2.left - textView1.right, isEqualAllowingError(space))\n        assertThat(textView3.left - textView2.right, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_AROUND\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.width - textView1.width - textView2.width - textView3.width\n        space /= 6 // Divide by the number of children * 2\n        assertTrue(space - 1 <= textView1.left && textView1.left <= space + 1)\n        val spaceInMiddle = space * 2\n        assertThat(textView2.left - textView1.right, isEqualAllowingError(spaceInMiddle))\n        assertThat(textView3.left - textView2.right, isEqualAllowingError(spaceInMiddle))\n        assertThat(flexboxLayout.right - textView3.right, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceEvenly() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_EVENLY\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_EVENLY))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.width - textView1.width - textView2.width - textView3.width\n        space /= 4 // Divide by the number of children + 1\n        assertThat(textView1.left, isEqualAllowingError(space))\n        assertThat(textView2.left - textView1.right, isEqualAllowingError(space))\n        assertThat(textView3.left - textView2.right, isEqualAllowingError(space))\n        assertThat(flexboxLayout.right - textView3.right, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_withPadding() {\n        val activity = activityRule.activity\n        val padding = 40\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_AROUND\n                        flexboxLayout.setPadding(padding, padding, padding, padding)\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.width - textView1.width - textView2.width - textView3.width -\n                padding * 2\n        space /= 6 // Divide by the number of children * 2\n        assertThat(textView1.left - padding, isEqualAllowingError(space))\n\n        val spaceInMiddle = space * 2\n        assertThat(textView2.left - textView1.right, isEqualAllowingError(spaceInMiddle))\n        assertThat(textView3.left - textView2.right, isEqualAllowingError(spaceInMiddle))\n        assertThat(flexboxLayout.right - textView3.right - padding, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceEvenly_withPadding() {\n        val activity = activityRule.activity\n        val padding = 40\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_EVENLY\n                        flexboxLayout.setPadding(padding, padding, padding, padding)\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_EVENLY))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.width - textView1.width - textView2.width - textView3.width -\n                padding * 2\n        space /= 4 // Divide by the number of children + 1\n        assertThat(textView1.left - padding, isEqualAllowingError(space))\n\n        assertThat(textView2.left - textView1.right, isEqualAllowingError(space))\n        assertThat(textView3.left - textView2.right, isEqualAllowingError(space))\n        assertThat(flexboxLayout.right - textView3.right - padding, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexStart_flexDirection_column() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.FLEX_START))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexEnd_flexDirection_column() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.FLEX_END\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.alignItems = AlignItems.STRETCH\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.FLEX_END))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyAbove(withId(R.id.text3)))\n        onView(withId(R.id.text1)).check(isCompletelyAbove(withId(R.id.text2)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_center_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.CENTER\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.CENTER))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.height - textView1.height - textView2.height - textView3.height\n        space /= 2\n        assertThat(textView1.top, isEqualAllowingError(space))\n        assertThat(flexboxLayout.bottom - textView3.bottom, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_BETWEEN\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.height - textView1.height - textView2.height - textView3.height\n        space /= 2\n        assertThat(textView2.top - textView1.bottom, isEqualAllowingError(space))\n        assertThat(textView3.top - textView2.bottom, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_flexDirection_column_withPadding() {\n        val activity = activityRule.activity\n        val padding = 40\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_BETWEEN\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.setPadding(padding, padding, padding, padding)\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.height - textView1.height - textView2.height - textView3.height - padding * 2\n        space /= 2\n        assertThat(textView1.top, `is`(padding))\n        assertThat(flexboxLayout.bottom - textView3.bottom, `is`(padding))\n        assertThat(textView2.top - textView1.bottom, isEqualAllowingError(space))\n        assertThat(textView3.top - textView2.bottom, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_AROUND\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.height - textView1.height - textView2.height - textView3.height\n        space /= 6 // Divide by the number of children * 2\n        assertThat(textView1.top, isEqualAllowingError(space))\n        val spaceInMiddle = space * 2\n        assertThat(textView2.top - textView1.bottom, isEqualAllowingError(spaceInMiddle))\n        assertThat(textView3.top - textView2.bottom, isEqualAllowingError(spaceInMiddle))\n        assertThat(flexboxLayout.bottom - textView3.bottom, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceEvenly_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_EVENLY\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_EVENLY))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.height - textView1.height - textView2.height - textView3.height\n        space /= 4 // Divide by the number of children + 1\n        assertThat(textView1.top, isEqualAllowingError(space))\n        assertThat(textView2.top - textView1.bottom, isEqualAllowingError(space))\n        assertThat(textView3.top - textView2.bottom, isEqualAllowingError(space))\n        assertThat(flexboxLayout.bottom - textView3.bottom, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_flexDirection_column_withPadding() {\n        val activity = activityRule.activity\n        val padding = 40\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_AROUND\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.setPadding(padding, padding, padding, padding)\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.height - textView1.height - textView2.height - textView3.height -\n                padding * 2\n        space /= 6 // Divide by the number of children * 2\n        assertThat(textView1.top - padding, isEqualAllowingError(space))\n        val spaceInMiddle = space * 2\n        assertThat(textView2.top - textView1.bottom, isEqualAllowingError(spaceInMiddle))\n        assertThat(textView3.top - textView2.bottom, isEqualAllowingError(spaceInMiddle))\n        assertThat(flexboxLayout.bottom - textView3.bottom - padding, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceEvenly_flexDirection_column_withPadding() {\n        val activity = activityRule.activity\n        val padding = 40\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_justify_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_EVENLY\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.setPadding(padding, padding, padding, padding)\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_EVENLY))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.height - textView1.height - textView2.height - textView3.height -\n                padding * 2\n        space /= 4 // Divide by the number of children + 1\n        assertThat(textView1.top - padding, isEqualAllowingError(space))\n        assertThat(textView2.top - textView1.bottom, isEqualAllowingError(space))\n        assertThat(textView3.top - textView2.bottom, isEqualAllowingError(space))\n        assertThat(flexboxLayout.bottom - textView3.bottom - padding,\n                isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_including_gone_views() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_justify_content_with_gone,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_AROUND\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.width - textView1.width - textView3.width\n        space /= 4 // Divide by the number of visible children * 2\n        assertThat(textView1.left, isEqualAllowingError(space))\n        val spaceInMiddle = space * 2\n        assertThat(textView3.left - textView1.right, isEqualAllowingError(spaceInMiddle))\n        assertThat(flexboxLayout.right - textView3.right, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_including_gone_views() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_justify_content_with_gone,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_BETWEEN\n                    }\n                })\n\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val space = flexboxLayout.width - textView1.width - textView3.width\n        assertThat(textView3.left - textView1.right, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_including_gone_views_direction_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_justify_content_with_gone,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_AROUND\n                    }\n                })\n\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var space = flexboxLayout.height - textView1.height - textView3.height\n        space /= 4 // Divide by the number of visible children * 2\n        assertThat(textView1.top, isEqualAllowingError(space))\n        val spaceInMiddle = space * 2\n        assertThat(textView3.top - textView1.bottom, isEqualAllowingError(spaceInMiddle))\n        assertThat(flexboxLayout.bottom - textView3.bottom, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_including_gone_views_direction_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_justify_content_with_gone,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.justifyContent = JustifyContent.SPACE_BETWEEN\n                    }\n                })\n\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val space = flexboxLayout.height - textView1.height - textView3.height\n        assertThat(textView3.top - textView1.bottom, isEqualAllowingError(space))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexGrow_withExactParentLength() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_grow_test)\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        // the third TextView is expanded to the right edge of the FlexboxLayout\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView3.width, `is`(flexboxLayout.width - textView1.width - textView2.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexGrow_withExactParentLength_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_grow_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        // the third TextView is expanded to the bottom edge of the FlexboxLayout\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView3.height, `is`(flexboxLayout.height - textView1.height - textView2.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexGrow_including_view_gone() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_grow_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val textView2 = activity.findViewById<TextView>(R.id.text2)\n                        textView2.visibility = View.GONE\n                    }\n                })\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        // the third TextView is expanded to the right edge of the FlexboxLayout\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView2.visibility, `is`(View.GONE))\n        assertThat(textView3.width, `is`(flexboxLayout.width - textView1.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_stretch() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test)\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.STRETCH))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        // the third TextView is wrapped to the next flex line\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val flexLineCrossSize = flexboxLayout.height / 2\n        // Two flex line's cross sizes are expanded to the half of the height of the FlexboxLayout.\n        // The third textView's top should be aligned width the second flex line.\n        assertThat(textView3.top, `is`(flexLineCrossSize))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_flexStart() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.FLEX_START\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.FLEX_START))\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        // the third TextView is wrapped to the next flex line\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView3.top, `is`(textView1.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_flexEnd() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.FLEX_END\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.FLEX_END))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isCompletelyAbove(withId(R.id.text3)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyAbove(withId(R.id.text3)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.bottom, `is`(flexboxLayout.bottom - textView3.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_flexEnd_parentPadding() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.FLEX_END\n                        flexboxLayout.setPadding(32, 32, 32, 32)\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.FLEX_END))\n        onView(withId(R.id.text1)).check(isCompletelyAbove(withId(R.id.text3)))\n        onView(withId(R.id.text2)).check(isCompletelyAbove(withId(R.id.text3)))\n\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView3.bottom, `is`(flexboxLayout.bottom - flexboxLayout.paddingBottom))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_flexEnd_parentPadding_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.FLEX_END\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                        flexboxLayout.setPadding(32, 32, 32, 32)\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.FLEX_END))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isCompletelyLeftOf(withId(R.id.text3)))\n        onView(withId(R.id.text2)).check(isCompletelyLeftOf(withId(R.id.text3)))\n\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView3.right, `is`(flexboxLayout.right - flexboxLayout.paddingRight))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_center() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.CENTER\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.CENTER))\n\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        var spaceAboveAndBottom = flexboxLayout.height - textView1.height - textView3.height\n        spaceAboveAndBottom /= 2\n\n        assertThat(textView1.top, isEqualAllowingError(spaceAboveAndBottom))\n        assertThat(flexboxLayout.bottom - textView3.bottom, isEqualAllowingError(spaceAboveAndBottom))\n        assertThat(flexboxLayout.flexLines.size, `is`(2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_spaceBetween() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.SPACE_BETWEEN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.SPACE_BETWEEN))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        assertThat(flexboxLayout.flexLines.size, `is`(2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_spaceBetween_withPadding() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.SPACE_BETWEEN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.SPACE_BETWEEN))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_spaceAround() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.SPACE_AROUND\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.SPACE_AROUND))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n\n        var spaceAround = flexboxLayout.height - textView1.height - textView3.height\n        spaceAround /= 4 // Divide by the number of flex lines * 2\n\n        assertThat(textView1.top, isEqualAllowingError(spaceAround))\n        val spaceInMiddle = textView1.bottom + spaceAround * 2\n        assertThat(textView3.top, isEqualAllowingError(spaceInMiddle))\n        assertThat(flexboxLayout.flexLines.size, `is`(2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_stretch_parentWrapContent() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val parentLp = flexboxLayout.layoutParams\n                        parentLp.height = ViewGroup.LayoutParams.WRAP_CONTENT\n                        flexboxLayout.layoutParams = parentLp\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.STRETCH))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        // the third TextView is wrapped to the next flex line\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        // alignContent is only effective if the parent's height/width mode is MeasureSpec.EXACTLY.\n        // The size of the flex lines don't change even if the alignContent is set to\n        // ALIGN_CONTENT_STRETCH\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView3.top, `is`(textView1.height))\n        assertThat(flexboxLayout.flexLines.size, `is`(2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_stretch_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.STRETCH))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        // the third TextView is wrapped to the next flex line\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val flexLineCrossSize = flexboxLayout.width / 2\n        // Two flex line's cross sizes are expanded to the half of the width of the FlexboxLayout.\n        // The third textView's left should be aligned with the second flex line.\n        assertThat(textView3.left, `is`(flexLineCrossSize))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_flexStart_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.FLEX_START\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.FLEX_START))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        // the third TextView is wrapped to the next flex line\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView3.left, `is`(textView1.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_flexEnd_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.FLEX_END\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.FLEX_END))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isCompletelyLeftOf(withId(R.id.text3)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text3)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.right, `is`(flexboxLayout.right - textView3.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_center_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.CENTER\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.CENTER))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val spaceLeftAndRight = (flexboxLayout.width - textView1.width - textView3.width) / 2\n\n        assertThat(textView1.left, isEqualAllowingError(spaceLeftAndRight))\n        assertThat(textView3.right, isEqualAllowingError(flexboxLayout.right - spaceLeftAndRight))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_spaceBetween_flexDirection_column() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.SPACE_BETWEEN\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.SPACE_BETWEEN))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_spaceAround_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.SPACE_AROUND\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.SPACE_AROUND))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n\n        var spaceAround = flexboxLayout.width - textView1.width - textView3.width\n        spaceAround /= 4 // Divide by the number of flex lines * 2\n\n        assertThat(textView1.left, isEqualAllowingError(spaceAround))\n        val spaceInMiddle = textView1.right + spaceAround * 2\n        assertThat(textView3.left, isEqualAllowingError(spaceInMiddle))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_stretch_parentWrapContent_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val parentLp = flexboxLayout.layoutParams\n                        parentLp.width = ViewGroup.LayoutParams.WRAP_CONTENT\n                        flexboxLayout.layoutParams = parentLp\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.STRETCH))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        // the third TextView is wrapped to the next flex line\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        // alignContent is only effective if the parent's height/width mode is MeasureSpec.EXACTLY.\n        // The size of the flex lines don't change even if the alignContent is set to\n        // ALIGN_CONTENT_STRETCH\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView3.left, `is`(textView1.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_flexEnd_wrapReverse_contentOverflowed() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test_overflowed,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.FLEX_END\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                    }\n                })\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.FLEX_END))\n        onView(withId(R.id.text6)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text5)).check(isCompletelyLeftOf(withId(R.id.text6)))\n        onView(withId(R.id.text4)).check(isCompletelyBelow(withId(R.id.text6)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_flexStart_wrapReverse_contentOverflowed() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test_overflowed,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.FLEX_START\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                    }\n                })\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.FLEX_START))\n        onView(withId(R.id.text1)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyAbove(withId(R.id.text1)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_spaceBetween_wrapReverse_contentOverflowed() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test_overflowed,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.SPACE_BETWEEN\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                    }\n                })\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.SPACE_BETWEEN))\n        onView(withId(R.id.text1)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyAbove(withId(R.id.text1)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_center_wrapReverse_contentOverflowed() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test_overflowed,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.CENTER\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                    }\n                })\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.CENTER))\n        val textView6 = activity.findViewById<TextView>(R.id.text6)\n        val textView4 = activity.findViewById<TextView>(R.id.text4)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n\n        assertThat(textView6.top - flexboxLayout.top, isEqualAllowingError(\n                (flexboxLayout.height - textView6.height - textView4.height - textView2.height) / 2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignContent_spaceAround_wrapReverse_contentOverflowed() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_content_test_overflowed,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignContent = AlignContent.SPACE_AROUND\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                    }\n                })\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.SPACE_AROUND))\n        val textView6 = activity.findViewById<TextView>(R.id.text6)\n        val textView4 = activity.findViewById<TextView>(R.id.text4)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n\n        assertThat(textView6.top - flexboxLayout.top, isEqualAllowingError(\n                (flexboxLayout.height - textView6.height - textView4.height - textView2.height) / 2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_stretch() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_stretch_test)\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.STRETCH))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.height / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.height, isEqualAllowingError(flexLineSize))\n        assertThat(textView2.height, isEqualAllowingError(flexLineSize))\n        assertThat(textView3.height, isEqualAllowingError(flexLineSize))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignSelf_stretch() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_align_self_stretch_test)\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        // Only the first TextView's alignSelf is set to ALIGN_SELF_STRETCH\n        val flexLineSize = flexboxLayout.height / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.height, isEqualAllowingError(flexLineSize))\n        assertThat(textView2.height, not(flexLineSize))\n        assertThat(textView3.height, not(flexLineSize))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignSelf_stretch_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_self_stretch_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        // Only the first TextView's alignSelf is set to ALIGN_SELF_STRETCH\n        val flexLineSize = flexboxLayout.width / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.width, isEqualAllowingError(flexLineSize))\n        assertThat(textView2.width, not(flexLineSize))\n        assertThat(textView3.width, not(flexLineSize))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_flexStart() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test)\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_START))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.height / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.height, not(flexLineSize))\n        assertThat(textView2.height, not(flexLineSize))\n        assertThat(textView3.height, not(flexLineSize))\n        assertThat(textView3.top, isEqualAllowingError(flexLineSize))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_flexEnd() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignItems = AlignItems.FLEX_END\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_END))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.height / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.height, not(flexLineSize))\n        assertThat(textView2.height, not(flexLineSize))\n        assertThat(textView3.height, not(flexLineSize))\n        assertThat(textView1.bottom, isEqualAllowingError(flexLineSize))\n        assertThat(textView2.bottom, isEqualAllowingError(flexLineSize))\n        assertThat(textView3.bottom, `is`(flexboxLayout.bottom))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_flexEnd_parentPadding() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_align_items_parent_padding_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignItems = AlignItems.FLEX_END\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_END))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        assertThat(textView1.bottom, `is`(flexboxLayout.bottom - flexboxLayout.paddingBottom))\n        assertThat(textView2.bottom, `is`(flexboxLayout.bottom - flexboxLayout.paddingBottom))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_flexEnd_parentPadding_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_align_items_parent_padding_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignItems = AlignItems.FLEX_END\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_END))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        assertThat(textView1.right, `is`(flexboxLayout.right - flexboxLayout.paddingRight))\n        assertThat(textView2.right, `is`(flexboxLayout.right - flexboxLayout.paddingRight))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_center() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignItems = AlignItems.CENTER\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.CENTER))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.height / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        // All TextView's heights are the same. No issues should be found if using the first\n        // TextView to calculate the space above and below\n        val spaceAboveAndBelow = (flexLineSize - textView1.height) / 2\n        assertThat(textView1.height, not(flexLineSize))\n        assertThat(textView2.height, not(flexLineSize))\n        assertThat(textView3.height, not(flexLineSize))\n        assertThat(textView1.top, isEqualAllowingError(spaceAboveAndBelow))\n        assertThat(textView2.top, isEqualAllowingError(spaceAboveAndBelow))\n        assertThat(textView3.top, isEqualAllowingError(flexLineSize + spaceAboveAndBelow))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_flexEnd_wrapReverse() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                        flexboxLayout.alignItems = AlignItems.FLEX_END\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_END))\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP_REVERSE))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.height / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n\n        assertThat(textView1.height, not(flexLineSize))\n        assertThat(textView2.height, not(flexLineSize))\n        assertThat(textView3.height, not(flexLineSize))\n        assertThat(textView1.top, isEqualAllowingError(flexboxLayout.height - flexLineSize))\n        assertThat(textView2.top, isEqualAllowingError(flexboxLayout.height - flexLineSize))\n        assertThat(textView3.top, `is`(0))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_center_wrapReverse() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                        flexboxLayout.alignItems = AlignItems.CENTER\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.CENTER))\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP_REVERSE))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.height / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n\n        // All TextView's heights are the same. No issues should be found if using the first\n        // TextView to calculate the space above and below\n        val spaceAboveAndBelow = (flexLineSize - textView1.height) / 2\n        assertThat(textView1.height, not(flexLineSize))\n        assertThat(textView2.height, not(flexLineSize))\n        assertThat(textView3.height, not(flexLineSize))\n        assertThat(textView1.bottom, isEqualAllowingError(flexboxLayout.height - spaceAboveAndBelow))\n        assertThat(textView2.bottom, isEqualAllowingError(flexboxLayout.height - spaceAboveAndBelow))\n        assertThat(textView3.bottom,\n                isEqualAllowingError(flexboxLayout.height - flexLineSize - spaceAboveAndBelow))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_flexStart_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_START))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.width / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.width, not(flexLineSize))\n        assertThat(textView2.width, not(flexLineSize))\n        assertThat(textView3.width, not(flexLineSize))\n        assertThat(textView3.left, isEqualAllowingError(flexLineSize))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_flexEnd_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignItems = AlignItems.FLEX_END\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_END))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.height / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.width, not(flexLineSize))\n        assertThat(textView2.width, not(flexLineSize))\n        assertThat(textView3.width, not(flexLineSize))\n        assertThat(textView1.right, isEqualAllowingError(flexLineSize))\n        assertThat(textView2.right, isEqualAllowingError(flexLineSize))\n        assertThat(textView3.right, `is`(flexboxLayout.right))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_center_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignItems = AlignItems.CENTER\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.CENTER))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.width / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        // All TextView's widths are the same. No issues should be found if using the first\n        // TextView to calculate the space left and right\n        val spaceLeftAndRight = (flexLineSize - textView1.width) / 2\n        assertThat(textView1.width, not(flexLineSize))\n        assertThat(textView2.width, not(flexLineSize))\n        assertThat(textView3.width, not(flexLineSize))\n        assertThat(textView1.left, isEqualAllowingError(spaceLeftAndRight))\n        assertThat(textView2.left, isEqualAllowingError(spaceLeftAndRight))\n        assertThat(textView3.left, isEqualAllowingError(flexLineSize + spaceLeftAndRight))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_flexEnd_wrapReverse_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                        flexboxLayout.alignItems = AlignItems.FLEX_END\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.FLEX_END))\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP_REVERSE))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.width / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n\n        assertThat(textView1.width, not(flexLineSize))\n        assertThat(textView2.width, not(flexLineSize))\n        assertThat(textView3.width, not(flexLineSize))\n        assertThat(textView1.left, isEqualAllowingError(flexboxLayout.width - flexLineSize))\n        assertThat(textView2.left, isEqualAllowingError(flexboxLayout.width - flexLineSize))\n        assertThat(textView3.left, `is`(0))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_center_wrapReverse_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_align_items_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n                        flexboxLayout.alignItems = AlignItems.CENTER\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.CENTER))\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP_REVERSE))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n\n        // There should be 2 flex lines in the layout with the given layout.\n        val flexLineSize = flexboxLayout.width / 2\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n\n        // All TextView's widths are the same. No issues should be found if using the first\n        // TextView to calculate the space above and below\n        val spaceLeftAndRight = (flexLineSize - textView1.width) / 2\n        assertThat(textView1.width, not(flexLineSize))\n        assertThat(textView2.width, not(flexLineSize))\n        assertThat(textView3.width, not(flexLineSize))\n        assertThat(textView1.right, isEqualAllowingError(flexboxLayout.width - spaceLeftAndRight))\n        assertThat(textView2.right, isEqualAllowingError(flexboxLayout.width - spaceLeftAndRight))\n        assertThat(textView3.right,\n                isEqualAllowingError(flexboxLayout.width - flexLineSize - spaceLeftAndRight))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_baseline() {\n        val activity = activityRule.activity\n        createFlexboxLayout(R.layout.activity_align_items_baseline_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val topPluBaseline1 = textView1.top + textView1.baseline\n        val topPluBaseline2 = textView2.top + textView2.baseline\n        val topPluBaseline3 = textView3.top + textView3.baseline\n\n        assertThat(topPluBaseline1, `is`(topPluBaseline2))\n        assertThat(topPluBaseline2, `is`(topPluBaseline3))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_baseline_wrapContent() {\n        // This test verifies the issue that baseline calculation is broken on API level +24\n        // https://github.com/google/flexbox-layout/issues/341\n        val activity = activityRule.activity\n        val layout = createFlexboxLayout(R.layout.activity_align_items_baseline_wrap_content)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val topPluBaseline1 = textView1.top + textView1.baseline\n        val topPluBaseline2 = textView2.top + textView2.baseline\n        val topPluBaseline3 = textView3.top + textView3.baseline\n\n        assertThat(topPluBaseline1, `is`(topPluBaseline2))\n        assertThat(topPluBaseline2, `is`(topPluBaseline3))\n        assertThat(layout.flexLines.size, `is`(1))\n        assertTrue(layout.flexLines[0].crossSize > textView1.height)\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_baseline_wrapReverse() {\n        val activity = activityRule.activity\n        createFlexboxLayout(R.layout.activity_align_items_baseline_test, object : Configuration {\n            override fun apply(flexboxLayout: FlexboxLayout) {\n                flexboxLayout.flexWrap = FlexWrap.WRAP_REVERSE\n            }\n        })\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val bottomPluBaseline1 = textView1.bottom + textView1.baseline\n        val bottomPluBaseline2 = textView2.bottom + textView2.baseline\n        val bottomPluBaseline3 = textView3.bottom + textView3.baseline\n\n        assertThat(bottomPluBaseline1, `is`(bottomPluBaseline2))\n        assertThat(bottomPluBaseline2, `is`(bottomPluBaseline3))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexDirection_row_reverse() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_wrap_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.ROW_REVERSE\n                    }\n                })\n\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n\n        // The layout direction should be right to left\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyLeftOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexDirection_column_reverse() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_wrap_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN_REVERSE\n                    }\n                })\n\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN_REVERSE))\n        onView(withId(R.id.text1)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyAbove(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexBasisPercent_wrap() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_flex_basis_percent_test)\n\n        // The text1 length is 50%, the text2 length is 60% and the wrap property is WRAP,\n        // the text2 should be on the second flex line.\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val lp1 = textView1.layoutParams as FlexboxLayout.LayoutParams\n        val lp2 = textView2.layoutParams as FlexboxLayout.LayoutParams\n        assertThat(textView1.width, `is`(Math.round(flexboxLayout.width * lp1.flexBasisPercent)))\n        assertThat(textView2.width, `is`(Math.round(flexboxLayout.width * lp2.flexBasisPercent)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexBasisPercent_nowrap() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_basis_percent_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.NOWRAP\n                    }\n                })\n\n        // The text1 length is 50%, the text2 length is 60% and the text3 has the fixed width,\n        // but the flex wrap attribute is NOWRAP, and flexShrink attributes for all\n        // children are the default value (1), three text views are shrank to fit in a single flex\n        // line.\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.NOWRAP))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val totalWidth = textView1.width + textView2.width + textView3.width\n        // Allowing minor different length with the flex container since the sum of the three text\n        // views width is not always the same as the flex container's main size caused by round\n        // errors in calculating the percent lengths.\n        assertThat(flexboxLayout.width, isEqualAllowingError(totalWidth))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexBasisPercent_wrap_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_basis_percent_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        // The text1 length is 50%, the text2 length is 60% and the wrap property is WRAP,\n        // the text2 should be on the second flex line.\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val lp1 = textView1.layoutParams as FlexboxLayout.LayoutParams\n        val lp2 = textView2.layoutParams as FlexboxLayout.LayoutParams\n        assertThat(textView1.height, `is`(Math.round(flexboxLayout.height * lp1.flexBasisPercent)))\n        assertThat(textView2.height, `is`(Math.round(flexboxLayout.height * lp2.flexBasisPercent)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexBasisPercent_nowrap_flexDirection_column() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_flex_basis_percent_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.NOWRAP\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n\n        // The text1 length is 50%, the text2 length is 60% and the text3 has the fixed height,\n        // but the flex wrap attribute is NOWRAP, and flexShrink attributes for all\n        // children are the default value (1), three text views are shrank to fit in a single\n        // flex line.\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.NOWRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val totalHeight = textView1.height + textView2.height + textView3.height\n        // Allowing minor different length with the flex container since the sum of the three text\n        // views width is not always the same as the flex container's main size caused by round\n        // errors in calculating the percent lengths.\n        assertThat(flexboxLayout.height, isEqualAllowingError(totalHeight))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMinWidth_initial_width_less_than_minWidth() {\n        val activity = activityRule.activity\n\n        // This test case verifies if the minWidth attribute works as a minimum constraint\n        // If the initial view width is less than the value of minWidth.\n        // The textView1's layout_width is set to wrap_content and its text is \"1\" apparently\n        // the initial measured width is less than the value of layout_minWidth (100dp)\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_minwidth_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val minWidth = (textView1.layoutParams as FlexboxLayout.LayoutParams).minWidth\n\n        onView(withId(R.id.text1)).check(hasWidth(minWidth))\n        onView(withId(R.id.text2)).check(hasWidth(flexboxLayout.width - minWidth))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMinWidth_works_as_lower_bound_shrink_to() {\n        val activity = activityRule.activity\n\n        // This test case verifies if the minWidth attribute works as a lower bound\n        // when the view would shrink less than the minWidth if the minWidth weren't set\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_minwidth_lower_bound_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val textView4 = activity.findViewById<TextView>(R.id.text4)\n        val minWidth = (textView1.layoutParams as FlexboxLayout.LayoutParams).minWidth\n\n        onView(withId(R.id.text1)).check(hasWidth(minWidth))\n        assertEquals(flexboxLayout.width, textView1.width + textView2.width + textView3.width +\n                textView4.width)\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMinHeight_initial_height_less_than_minHeight() {\n        val activity = activityRule.activity\n\n        // This test case verifies if the minHeight attribute works as a minimum constraint\n        // If the initial view height is less than the value of minHeight.\n        // The textView1's layout_height is set to wrap_content and its text is \"1\" apparently\n        // the initial measured height is less than the value of layout_minHeight (100dp)\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_minheight_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val minHeight = (textView1.layoutParams as FlexboxLayout.LayoutParams).minHeight\n\n        onView(withId(R.id.text1)).check(hasHeight(minHeight))\n        onView(withId(R.id.text2)).check(hasHeight(flexboxLayout.height - minHeight))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMinHeight_works_as_lower_bound_shrink_to() {\n        val activity = activityRule.activity\n\n        // This test case verifies if the minHeight attribute works as a lower bound\n        // when the view would shrink less than the minHeight if the minHeight weren't set\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_minheight_lower_bound_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val textView4 = activity.findViewById<TextView>(R.id.text4)\n        val minHeight = (textView1.layoutParams as FlexboxLayout.LayoutParams).minHeight\n\n        onView(withId(R.id.text1)).check(hasHeight(minHeight))\n        assertEquals(flexboxLayout.height, textView1.height + textView2.height + textView3.height +\n                textView4.height)\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMaxWidth_initial_width_more_than_maxWidth() {\n        val activity = activityRule.activity\n\n        // This test case verifies if the maxWidth attribute works as a maximum constraint\n        // ff the initial view width is more than the value of maxWidth.\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_maxwidth_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val maxWidth = (textView1.layoutParams as FlexboxLayout.LayoutParams).maxWidth\n\n        onView(withId(R.id.text1)).check(hasWidth(maxWidth))\n        onView(withId(R.id.text2)).check(hasWidth(flexboxLayout.width - maxWidth))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMaxWidth_works_as_upper_bound_expand_to() {\n        val activity = activityRule.activity\n\n        // This test case verifies if the maxWidth attribute works as a upper bound\n        // when the view would expand more than the maxWidth if the maxWidth weren't set\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_maxwidth_upper_bound_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val maxWidth = (textView1.layoutParams as FlexboxLayout.LayoutParams).maxWidth\n\n        onView(withId(R.id.text1)).check(hasWidth(maxWidth))\n        assertEquals(flexboxLayout.width, textView1.width + textView2.width)\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMaxHeight_initial_height_more_than_maxHeight() {\n        val activity = activityRule.activity\n\n        // This test case verifies if the maxHeight attribute works as a maximum constraint\n        // ff the initial view height is more than the value of maxHeight.\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_maxheight_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val maxHeight = (textView1.layoutParams as FlexboxLayout.LayoutParams).maxHeight\n\n        onView(withId(R.id.text1)).check(hasHeight(maxHeight))\n        onView(withId(R.id.text2)).check(hasHeight(flexboxLayout.height - maxHeight))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMaxHeight_works_as_lower_bound_expand_to() {\n        val activity = activityRule.activity\n\n        // This test case verifies if the maxHeight attribute works as a upper bound\n        // when the view would expand more than the maxHeight if the maxHeight weren't set\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_maxheight_upper_bound_test)\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val maxHeight = (textView1.layoutParams as FlexboxLayout.LayoutParams).maxHeight\n\n        onView(withId(R.id.text1)).check(hasHeight(maxHeight))\n        assertEquals(flexboxLayout.height, textView1.height + textView2.height)\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testView_visibility_gone() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_views_visibility_gone)\n\n        // The text1 and text2's visibility are gone, so the visible view starts from text3\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text4)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text4)).check(isCompletelyRightOf(withId(R.id.text3)))\n        onView(withId(R.id.text5)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text5)).check(isCompletelyBelow(withId(R.id.text3)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        val textView4 = activity.findViewById<TextView>(R.id.text4)\n        val textView5 = activity.findViewById<TextView>(R.id.text5)\n        assertThat(textView1.visibility, `is`(View.GONE))\n        assertThat(textView2.visibility, `is`(View.GONE))\n        assertThat(textView4.left, `is`(textView3.right))\n        assertThat(textView5.top, `is`(textView3.bottom))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testView_visibility_gone_first_item_in_flex_line_horizontal() {\n        // This test verifies if the FlexboxLayout is visible when the visibility of the first\n        // flex item in the second flex line (or arbitrary flex lines other than the first flex\n        // line) is set to \"gone\"\n        // There was an issue reported for that\n        // https://github.com/google/flexbox-layout/issues/47\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_visibility_gone_first_item_in_flex_line_row)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n\n        assertTrue(flexboxLayout.height > 0)\n        assertThat(flexboxLayout.height, `is`(textView1.height + textView3.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testView_visibility_gone_first_item_in_flex_line_vertical() {\n        // This test verifies if the FlexboxLayout is visible when the visibility of the first\n        // flex item in the second flex line (or arbitrary flex lines other than the first flex\n        // line) is set to \"gone\"\n        // There was an issue reported for that\n        // https://github.com/google/flexbox-layout/issues/47\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_visibility_gone_first_item_in_flex_line_column)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n\n        assertTrue(flexboxLayout.width > 0)\n        assertThat(flexboxLayout.width, `is`(textView1.width + textView3.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testView_visibility_invisible() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_views_visibility_invisible)\n\n        // The text1 and text2's visibility are invisible, these views take space like visible views\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(textView1.visibility, `is`(View.INVISIBLE))\n        assertThat(textView2.visibility, `is`(View.INVISIBLE))\n        assertThat(textView3.top, `is`(textView1.bottom))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testWrapBefore() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_wrap_before_test)\n\n        // layout_wrapBefore for the text2 and text3 are set to true, the text2 and text3 should\n        // be the first item for each flex line.\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        val textView1 = activity.findViewById<TextView>(R.id.text1)\n        val textView2 = activity.findViewById<TextView>(R.id.text2)\n        val textView3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(flexboxLayout.height, `is`(textView1.height + textView2.height + textView3.height))\n\n        activityRule.runOnUiThread {\n            val lp2 = textView2.layoutParams as FlexboxLayout.LayoutParams\n            lp2.isWrapBefore = false\n            textView2.layoutParams = lp2\n        }\n\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n        assertThat(flexboxLayout.height, `is`(textView1.height + textView3.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testWrapBefore_nowrap() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_wrap_before_test,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexWrap = FlexWrap.NOWRAP\n                    }\n                })\n\n        // layout_wrapBefore for the text2 and text3 are set to true, but the flexWrap is set to\n        // NOWRAP, three text views should not be wrapped.\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.NOWRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text2)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testWrap_parentPadding_horizontal() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_wrap_parent_padding_horizontal_test)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        // The sum of width of TextView1 and TextView2 is not enough for wrapping, but considering\n        // parent padding, the second TextView should be wrapped\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        assertThat(flexboxLayout.height, `is`(flexboxLayout.paddingTop + flexboxLayout.paddingBottom +\n                text1.height + text2.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testWrap_parentPadding_vertical() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_wrap_parent_padding_vertical_test)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        // The sum of height of TextView1 and TextView2 is not enough for wrapping, but considering\n        // parent padding, the second TextView should be wrapped\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        assertThat(flexboxLayout.width, `is`(flexboxLayout.paddingLeft + flexboxLayout.paddingRight +\n                text1.width + text2.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testWrap_childMargin_horizontal() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_wrap_child_margin_horizontal_test)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        // The sum of width of TextView1 and TextView2 is not enough for wrapping, but considering\n        // the margin for the TextView2, the second TextView should be wrapped\n        onView(withId(R.id.text2)).check(isCompletelyBelow(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyRightOf(withId(R.id.text2)))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val lp2 = text2.layoutParams as FlexboxLayout.LayoutParams\n        assertThat(flexboxLayout.height, `is`(text1.height + text2.height + lp2.topMargin +\n                lp2.bottomMargin))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstItemLarge_horizontal() {\n        // This test verifies a empty flex line is not added when the first flex item is large\n        // and judged wrapping is required with the first item.\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_first_item_large_horizontal_test)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.STRETCH))\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.STRETCH))\n        // The sum of width of TextView1 and TextView2 is not enough for wrapping, but considering\n        // the margin for the TextView2, the second TextView should be wrapped\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(flexboxLayout.height, `is`(text1.height + text2.height + text3.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstItemLarge_vertical() {\n        // This test verifies a empty flex line is not added when the first flex item is large\n        // and judged wrapping is required with the first item.\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_first_item_large_vertical_test)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.alignItems, `is`(AlignItems.STRETCH))\n        assertThat(flexboxLayout.alignContent, `is`(AlignContent.STRETCH))\n        // The sum of width of TextView1 and TextView2 is not enough for wrapping, but considering\n        // the margin for the TextView2, the second TextView should be wrapped\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        assertThat(flexboxLayout.width, `is`(text1.width + text2.width + text3.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testWrap_childMargin_vertical() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_wrap_child_margin_vertical_test)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        // The sum of height of TextView1 and TextView2 is not enough for wrapping, but considering\n        // the margin of the TextView2, the second TextView should be wrapped\n        onView(withId(R.id.text2)).check(isCompletelyRightOf(withId(R.id.text1)))\n        onView(withId(R.id.text3)).check(isCompletelyBelow(withId(R.id.text2)))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val lp2 = text2.layoutParams as FlexboxLayout.LayoutParams\n        assertThat(flexboxLayout.width,\n                `is`(text1.width + text2.width + lp2.leftMargin + lp2.rightMargin))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testEmptyChildren() {\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_empty_children)\n\n        assertThat(flexboxLayout.childCount, `is`(0))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_verticalBeginning() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_divider_test_direction_row)\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val widthSumFirstRow = text1.width + text2.width + text3.width + divider!!.intrinsicWidth\n        assertThat(text3.right, `is`(widthSumFirstRow))\n        assertThat(text1.left, `is`(not(flexboxLayout.left)))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        // The right should be 90 * 3 + 10 (divider)\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(280)))\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        val flexLine2 = flexLines[1]\n        // The right should be 140 * 2 + 10 (divider)\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(290)))\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_verticalMiddle() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_row,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_MIDDLE\n                    }\n                }\n        )\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_MIDDLE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        // Three text views are placed in the first row, thus two vertical middle dividers should\n        // be placed\n        val widthSumFirstRow = text1.width + text2.width + text3.width + divider!!.intrinsicWidth * 2\n        assertThat(text3.right, `is`(widthSumFirstRow))\n        assertThat(text1.left, `is`(flexboxLayout.left))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        // The right should be 90 * 3 + 10 * 2(divider)\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(290)))\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        val flexLine2 = flexLines[1]\n        // The right should be 140 * 2 + 10 (divider)\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(290)))\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_verticalEnd() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_row,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_END\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_END))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        // Three text views are placed in the first row, thus two vertical middle dividers should\n        // be placed\n        val widthSumFirstRow = text1.width + text2.width + text3.width + divider!!.intrinsicWidth\n        assertThat(text3.right + divider.intrinsicWidth, `is`(widthSumFirstRow))\n        assertThat(text1.left, `is`(flexboxLayout.left))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        // The right should be 90 * 3 + 10 (divider)\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(280)))\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        val flexLine2 = flexLines[1]\n        // The right should be 140 * 2 + 10 (divider)\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(290)))\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_verticalAll() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_row,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or FlexboxLayout.SHOW_DIVIDER_END\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerVertical,\n                `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or\n                        FlexboxLayout.SHOW_DIVIDER_END))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        // Three text views are placed in the first row, thus two vertical middle dividers should\n        // be placed\n        val widthSumFirstRow = text1.width + text2.width + text3.width + divider!!.intrinsicWidth * 4\n        assertThat(text3.right + divider.intrinsicWidth, `is`(widthSumFirstRow))\n        assertThat(text1.left, `is`(not(flexboxLayout.left)))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        // The right should be 90 * 3 + 10 * 4 (divider)\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(310)))\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        val flexLine2 = flexLines[1]\n        // The right should be 140 * 2 + 10 * 3 (divider)\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(310)))\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_horizontalBeginning() {\n        val activity = activityRule.activity\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_row,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.dividerDrawableHorizontal = divider\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_BEGINNING\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_NONE\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_NONE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        assertNotNull(divider)\n        val heightSum = text1.height + text4.height + divider!!.intrinsicHeight\n        assertThat(text4.bottom, `is`(heightSum))\n        assertThat(text1.top, `is`(not(flexboxLayout.top)))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        // There is a horizontal divider at the beginning. Top and bottom coordinates are shifted\n        // by the amount of 15\n        // The right should be 90 * 3\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        val flexLine2 = flexLines[1]\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(280)))\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_horizontalMiddle() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_row,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val divider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider, null)\n                        flexboxLayout.dividerDrawableHorizontal = divider\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_MIDDLE\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_NONE\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_MIDDLE))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_NONE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val heightSum = text1.height + text4.height + divider!!.intrinsicHeight\n        assertThat(text4.bottom, `is`(heightSum))\n        assertThat(text1.top, `is`(flexboxLayout.top))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        // The right should be 90 * 3\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // There is a horizontal divider at the middle. Top and bottom coordinates are shifted\n        // by the amount of 15\n        val flexLine2 = flexLines[1]\n        // The right should be 140\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(280)))\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_horizontalEnd() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_row,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val divider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider, null)\n                        flexboxLayout.dividerDrawableHorizontal = divider\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_END\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_NONE\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_END))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_NONE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val heightSum = text1.height + text4.height + divider!!.intrinsicHeight\n        assertThat(text4.bottom + divider.intrinsicHeight, `is`(heightSum))\n        assertThat(text1.top, `is`(flexboxLayout.top))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        // The right should be 90 * 3\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // There is a horizontal divider at the middle. Top and bottom coordinates are shifted\n        // by the amount of 15\n        val flexLine2 = flexLines[1]\n        // The right should be 140\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(280)))\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_horizontalAll() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_row,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val divider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider, null)\n                        flexboxLayout.dividerDrawableHorizontal = divider\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or FlexboxLayout.SHOW_DIVIDER_END\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_NONE\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerHorizontal,\n                `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or\n                        FlexboxLayout.SHOW_DIVIDER_END))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_NONE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val heightSum = text1.height + text4.height + divider!!.intrinsicHeight * 3\n        assertThat(text4.bottom + divider.intrinsicHeight, `is`(heightSum))\n        assertThat(text1.top, `is`(not(flexboxLayout.top)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionRow_all_thickDivider() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_row,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val thickDivider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider_thick, null)\n                        flexboxLayout.dividerDrawableVertical = thickDivider\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or FlexboxLayout.SHOW_DIVIDER_END\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(flexboxLayout.showDividerVertical,\n                `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or\n                        FlexboxLayout.SHOW_DIVIDER_END))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider_thick, null)\n        // The sum of three text views and the sum of thick dividers don't fit in one line.\n        // The last text view should be placed to the next line.\n        assertNotNull(divider)\n        val widthSumFirstRow = text1.width + text2.width + divider!!.intrinsicWidth * 3\n        assertThat(text2.right + divider.intrinsicWidth, `is`(widthSumFirstRow))\n        assertThat(text1.left, `is`(not(flexboxLayout.left)))\n        assertThat(text3.bottom, `is`(text1.height + text2.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_horizontalBeginning() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_divider_test_direction_column)\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val heightSumFirstRow = text1.height + text2.height + text3.height + divider!!.intrinsicHeight\n        assertThat(text3.bottom, `is`(heightSumFirstRow))\n        assertThat(text1.top, `is`(not(flexboxLayout.top)))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // The bottom should be 90 * 3 + 15\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(285)))\n        val flexLine2 = flexLines[1]\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // The bottom should be 140 * 2 + 15\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(295)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_horizontalMiddle() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_MIDDLE\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_MIDDLE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val heightSumFirstRow = text1.height + text2.height + text3.height + divider!!.intrinsicHeight * 2\n        assertThat(text3.bottom, `is`(heightSumFirstRow))\n        assertThat(text1.top, `is`(flexboxLayout.top))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // The bottom should be 90 * 3 + 15 * 2\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(300)))\n        val flexLine2 = flexLines[1]\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // The bottom should be 140 * 2 + 15\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(295)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_horizontalEnd() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_END\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_END))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val heightSumFirstRow = text1.height + text2.height + text3.height + divider!!.intrinsicHeight\n        assertThat(text3.bottom + divider.intrinsicHeight, `is`(heightSumFirstRow))\n        assertThat(text1.top, `is`(flexboxLayout.top))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // The bottom should be 90 * 3 + 15\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(285)))\n        val flexLine2 = flexLines[1]\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // The bottom should be 140 * 2 + 15\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(295)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_horizontalAll() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or FlexboxLayout.SHOW_DIVIDER_END\n                    }\n                }\n        )\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerHorizontal,\n                `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or\n                        FlexboxLayout.SHOW_DIVIDER_END))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val heightSumFirstRow = text1.height + text2.height + text3.height + divider!!.intrinsicHeight * 4\n        assertThat(text3.bottom + divider.intrinsicHeight, `is`(heightSumFirstRow))\n        assertThat(text1.top, `is`(not(flexboxLayout.top)))\n        val flexLines = flexboxLayout.flexLines\n        assertThat(flexLines.size, `is`(2))\n        val flexLine1 = flexLines[0]\n        assertThat(flexLine1.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // The bottom should be 90 * 3 + 15 * 4\n        assertThat(flexLine1.mainSize, isEqualAllowingError(activity.dpToPixel(330)))\n        val flexLine2 = flexLines[1]\n        assertThat(flexLine2.crossSize, isEqualAllowingError(activity.dpToPixel(80)))\n        // The bottom should be 140 * 2 + 15 * 3\n        assertThat(flexLine2.mainSize, isEqualAllowingError(activity.dpToPixel(325)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_verticalBeginning() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val divider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider, null)\n                        flexboxLayout.dividerDrawableVertical = divider\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_BEGINNING\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_NONE\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_NONE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val widthSum = text1.width + text4.width + divider!!.intrinsicWidth\n        assertThat(text4.right, `is`(widthSum))\n        assertThat(text1.left, `is`(not(flexboxLayout.left)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_verticalMiddle() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val divider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider, null)\n                        flexboxLayout.dividerDrawableVertical = divider\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_MIDDLE\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_NONE\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_MIDDLE))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_NONE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val widthSum = text1.width + text4.width + divider!!.intrinsicWidth\n        assertThat(text4.right, `is`(widthSum))\n        assertThat(text1.left, `is`(flexboxLayout.left))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_verticalEnd() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val divider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider, null)\n                        flexboxLayout.dividerDrawableHorizontal = divider\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_END\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_NONE\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerVertical, `is`(FlexboxLayout.SHOW_DIVIDER_END))\n        assertThat(flexboxLayout.showDividerHorizontal, `is`(FlexboxLayout.SHOW_DIVIDER_NONE))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val widthSum = text1.width + text4.width + divider!!.intrinsicWidth\n        assertThat(text4.right + divider.intrinsicWidth, `is`(widthSum))\n        assertThat(text1.left, `is`(flexboxLayout.left))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_verticalAll() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val divider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider, null)\n                        flexboxLayout.dividerDrawableVertical = divider\n                        flexboxLayout.showDividerVertical = FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or FlexboxLayout.SHOW_DIVIDER_END\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_NONE\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerVertical,\n                `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or\n                        FlexboxLayout.SHOW_DIVIDER_END))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val widthSum = text1.width + text4.width + divider!!.intrinsicWidth * 3\n        assertThat(text4.right + divider.intrinsicWidth, `is`(widthSum))\n        assertThat(text1.left, `is`(not(flexboxLayout.left)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_vertical_horizontal_All() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val divider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider, null)\n                        flexboxLayout.setDividerDrawable(divider)\n                        flexboxLayout.setShowDivider(\n                                FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or FlexboxLayout.SHOW_DIVIDER_END)\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerVertical,\n                `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or\n                        FlexboxLayout.SHOW_DIVIDER_END))\n        assertThat(flexboxLayout.showDividerHorizontal,\n                `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or\n                        FlexboxLayout.SHOW_DIVIDER_END))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val text4 = activity.findViewById<TextView>(R.id.text4)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        assertNotNull(divider)\n        val heightSum = text1.height + text2.height + text3.height + divider!!.intrinsicHeight * 4\n        val widthSum = text1.width + text4.width + divider.intrinsicWidth * 3\n        assertThat(text3.bottom + divider.intrinsicHeight, `is`(heightSum))\n        assertThat(text4.right + divider.intrinsicWidth, `is`(widthSum))\n        assertThat(text1.left, `is`(not(flexboxLayout.left)))\n        assertThat(text1.top, `is`(not(flexboxLayout.top)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDivider_directionColumn_all_thickDivider() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_divider_test_direction_column,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        val thickDivider = ResourcesCompat\n                                .getDrawable(activity.resources, R.drawable.divider_thick, null)\n                        flexboxLayout.dividerDrawableHorizontal = thickDivider\n                        flexboxLayout.showDividerHorizontal = FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or FlexboxLayout.SHOW_DIVIDER_END\n                    }\n                })\n\n        assertThat(flexboxLayout.flexWrap, `is`(FlexWrap.WRAP))\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayout.showDividerHorizontal,\n                `is`(FlexboxLayout.SHOW_DIVIDER_BEGINNING or FlexboxLayout.SHOW_DIVIDER_MIDDLE or\n                        FlexboxLayout.SHOW_DIVIDER_END))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        val text3 = activity.findViewById<TextView>(R.id.text3)\n        val divider = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider_thick, null)\n        // The sum of three text views and the sum of thick dividers don't fit in one line.\n        // The last text view should be placed to the next line.\n        assertNotNull(divider)\n        val heightSum = text1.height + text2.height + divider!!.intrinsicHeight * 3\n        assertThat(text2.bottom + divider.intrinsicHeight, `is`(heightSum))\n        assertThat(text1.top, `is`(not(flexboxLayout.top)))\n        assertThat(text3.right, `is`(text1.width + text3.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testZeroWidth_wrapContentHeight_positiveFlexGrow() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_zero_width_positive_flexgrow)\n\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        // Both text view's layout_width is set to 0dp, layout_height is set to wrap_content and\n        // layout_flexGrow is set to 1. And the text2 has a longer text than the text1.\n        // So if the cross size calculation (height) is wrong, the height of two text view do not\n        // match because text2 is trying to expand vertically.\n        // This assertion verifies that isn't happening. Finally both text views expand horizontally\n        // enough to contain their texts in one line.\n        assertThat(text1.height, `is`(text2.height))\n        assertThat(text1.width + text2.width, isEqualAllowingError(flexboxLayout.width))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testZeroHeight_wrapContentWidth_positiveFlexGrow() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_zero_height_positive_flexgrow)\n\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        val text2 = activity.findViewById<TextView>(R.id.text2)\n        assertThat(text1.width, `is`(not(text2.width)))\n        assertThat(text1.height + text2.height, isEqualAllowingError(flexboxLayout.height))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexDirection_row_alignItems_center_margin_oneSide() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_direction_row_align_items_center_margin_oneside)\n\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.ROW))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        assertThat(text1.top, isEqualAllowingError(activity.dpToPixel(30)))\n        assertThat(flexboxLayout.bottom - text1.bottom, isEqualAllowingError(activity.dpToPixel(50)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexDirection_column_alignItems_center_margin_oneSide() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_direction_column_align_items_center_margin_oneside)\n\n        assertThat(flexboxLayout.flexDirection, `is`(FlexDirection.COLUMN))\n\n        val text1 = activity.findViewById<TextView>(R.id.text1)\n        assertThat(text1.left, isEqualAllowingError(activity.dpToPixel(30)))\n        assertThat(flexboxLayout.right - text1.right, isEqualAllowingError(activity.dpToPixel(50)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChildBottomMarginIncluded_flexContainerWrapContent_directionRow_flexGrow() {\n        // This test is to verify the case where:\n        //   - layout_height is set to wrap_content for the FlexboxLayout\n        //   - Bottom (or top) margin is set to a child\n        //   - The child which the has the bottom (top) margin has the largest height in the\n        //     same flex line (or only a single child exists)\n        //   - The child has a positive layout_flexGrow attribute set\n        //  If these conditions were met, the height of the FlexboxLayout didn't take the bottom\n        //  margin on the child into account\n        //  See https://github.com/google/flexbox-layout/issues/154\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_wrap_content_child_bottom_margin_row_grow)\n\n        // layout_height for text1: 24dp, layout_marginBottom: 12dp\n        assertThat(flexboxLayout.height, isEqualAllowingError(activityRule.activity.dpToPixel(36)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChildEndMarginIncluded_flexContainerWrapContent_directionColumn_flexGrow() {\n        // This test is to verify the case where:\n        //   - layout_width is set to wrap_content for the FlexboxLayout\n        //   - End (or start) margin is set to a child\n        //   - The child which the has the end (start) margin has the largest width in the\n        //     same flex line (or only a single child exists)\n        //   - The child has a positive layout_flexGrow attribute set\n        //  If these conditions were met, the width of the FlexboxLayout didn't take the bottom\n        //  margin on the child into account\n        //  See https://github.com/google/flexbox-layout/issues/154\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_wrap_content_child_bottom_margin_column_grow)\n\n        // layout_width for text1: 24dp, layout_marginEnd: 12dp\n        assertThat(flexboxLayout.width, isEqualAllowingError(activityRule.activity.dpToPixel(36)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChildBottomMarginIncluded_flexContainerWrapContent_directionRow_flexShrink() {\n        // This test is to verify the case where:\n        //   - layout_height is set to wrap_content for the FlexboxLayout\n        //   - flex_wrap is set to nowrap for the FlexboxLayout\n        //   - Bottom (or top) margin is set to a child\n        //   - The child which the has the bottom (top) margin has the largest height in the\n        //     same flex line\n        //   - The child has a positive layout_flexShrink attribute set\n        //   - The sum of children width overflows parent's width (shrink will happen)\n        //  If these conditions were met, the height of the FlexboxLayout didn't take the bottom\n        //  margin on the child into account\n        //  See https://github.com/google/flexbox-layout/issues/154\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_wrap_content_child_bottom_margin_row_shrink)\n\n        // layout_height for text1: 24dp, layout_marginBottom: 12dp\n        assertThat(flexboxLayout.height, isEqualAllowingError(activityRule.activity.dpToPixel(36)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChildBottomMarginIncluded_flexContainerWrapContent_directionColumn_flexShrink() {\n        // This test is to verify the case where:\n        //   - layout_width is set to wrap_content for the FlexboxLayout\n        //   - flex_wrap is set to nowrap for the FlexboxLayout\n        //   - End (or start) margin is set to a child\n        //   - The child which the has the end (start) margin has the largest width in the\n        //     same flex line\n        //   - The child has a positive layout_flexShrink attribute set\n        //   - The sum of children height overflows parent's height (shrink will happen)\n        //  If these conditions were met, the height of the FlexboxLayout didn't take the bottom\n        //  margin on the child into account\n        //  See https://github.com/google/flexbox-layout/issues/154\n        val flexboxLayout = createFlexboxLayout(\n                R.layout.activity_wrap_content_child_bottom_margin_column_shrink)\n\n        // layout_width for text1: 24dp, layout_marginEnd: 12dp\n        assertThat(flexboxLayout.width, isEqualAllowingError(activityRule.activity.dpToPixel(36)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChildNeedsRemeasure_row() {\n        createFlexboxLayout(R.layout.activity_child_needs_remeasure_row)\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChildNeedsRemeasure_column() {\n        createFlexboxLayout(R.layout.activity_child_needs_remeasure_column)\n        onView(withId(R.id.text1)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text1)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstViewGone_firstLineSingleItem_row() {\n        // This test verifies the case where the first view's visibility is gone and the second\n        // view is in the next flex line. In that case, the second view's position is misplaced.\n        // https://github.com/google/flexbox-layout/issues/283\n        createFlexboxLayout(R.layout.activity_first_view_gone_first_line_single_item)\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstViewGone_firstLineSingleItem_column() {\n        // This test verifies the case where the first view's visibility is gone and the second\n        // view is in the next flex line. In that case, the second view's position is misplaced.\n        // https://github.com/google/flexbox-layout/issues/283\n        createFlexboxLayout(R.layout.activity_first_view_gone_first_line_single_item,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstViewGone_flexGrowSetForRestOfItems_row() {\n        // This test verifies the case where the first view's visibility is gone and the second\n        // view and third view have the layout_flexGrow attribute set. In that case, the second\n        // view's position is misplaced and the third view becomes invisible .\n        // https://github.com/google/flexbox-layout/issues/303\n        createFlexboxLayout(R.layout.activity_first_view_gone_layout_grow_set_for_rest)\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isRightAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstViewGone_flexGrowSetForRestOfItems_column() {\n        // This test verifies the case where the first view's visibility is gone and the second\n        // view and third view have the layout_flexGrow attribute set. In that case, the second\n        // view's position is misplaced and the third view becomes invisible .\n        // https://github.com/google/flexbox-layout/issues/303\n        createFlexboxLayout(R.layout.activity_first_view_gone_layout_grow_set_for_rest,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isBottomAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstViewGone_flexShrinkSetForRestOfItems_row() {\n        createFlexboxLayout(R.layout.activity_first_view_gone_layout_shrink_set_for_rest)\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstViewGone_flexShrinkSetForRestOfItems_column() {\n        createFlexboxLayout(R.layout.activity_first_view_gone_layout_shrink_set_for_rest,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.flexDirection = FlexDirection.COLUMN\n                    }\n                })\n        onView(withId(R.id.text2)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text2)).check(isLeftAlignedWith(withId(R.id.flexbox_layout)))\n        onView(withId(R.id.text3)).check(isTopAlignedWith(withId(R.id.flexbox_layout)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAddItemProgrammatically_withMarginLayoutParams() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_empty_children,\n        object : Configuration {\n            override fun apply(flexboxLayout: FlexboxLayout) {\n                flexboxLayout.alignItems = AlignItems.FLEX_START\n                val first = createTextView(activity, \"1\", 0)\n                val second = createTextView(activity, \"2\", 0)\n                val lp1 = ViewGroup.MarginLayoutParams(100, 100)\n                lp1.setMargins(10, 10, 10, 10)\n                val lp2 = ViewGroup.MarginLayoutParams(100, 100)\n                lp2.setMargins(20, 20, 20, 20)\n                first.layoutParams = lp1\n                second.layoutParams = lp2\n                flexboxLayout.addView(first)\n                flexboxLayout.addView(second)\n            }\n        })\n\n        assertThat(flexboxLayout.childCount, `is`(2))\n        val view1 = flexboxLayout.getChildAt(0)\n        val view2 = flexboxLayout.getChildAt(1)\n        // Assert the coordinates of the views added programmatically with margins\n        assertThat(view1.left, `is`(10))\n        assertThat(view1.top, `is`(10))\n        assertThat(view1.bottom, `is`(110))\n        assertThat(view1.right, `is`(110))\n        assertThat(view2.left, `is`(140))\n        assertThat(view2.top, `is`(20))\n        assertThat(view2.bottom, `is`(120))\n        assertThat(view2.right, `is`(240))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAddItemProgrammatically_withFlexboxLayoutLayoutParams() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_empty_children,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.alignItems = AlignItems.FLEX_START\n                        val first = createTextView(activity, \"1\", 0)\n                        val second = createTextView(activity, \"2\", 0)\n                        val lp1 = FlexboxLayout.LayoutParams(100, 100)\n                        lp1.setMargins(10, 10, 10, 10)\n                        val lp2 = FlexboxLayout.LayoutParams(100, 100)\n                        lp2.setMargins(20, 20, 20, 20)\n                        first.layoutParams = lp1\n                        second.layoutParams = lp2\n                        flexboxLayout.addView(first)\n                        flexboxLayout.addView(second)\n                    }\n                })\n\n        assertThat(flexboxLayout.childCount, `is`(2))\n        val view1 = flexboxLayout.getChildAt(0)\n        val view2 = flexboxLayout.getChildAt(1)\n        // Assert the coordinates of the views added programmatically with margins\n        assertThat(view1.left, `is`(10))\n        assertThat(view1.top, `is`(10))\n        assertThat(view1.bottom, `is`(110))\n        assertThat(view1.right, `is`(110))\n        assertThat(view2.left, `is`(140))\n        assertThat(view2.top, `is`(20))\n        assertThat(view2.bottom, `is`(120))\n        assertThat(view2.right, `is`(240))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMaxLines() {\n        val activity = activityRule.activity\n        val flexboxLayout = createFlexboxLayout(R.layout.activity_empty_children,\n                object : Configuration {\n                    override fun apply(flexboxLayout: FlexboxLayout) {\n                        flexboxLayout.maxLine = 3\n                        for (i in 1..50) {\n                            val textView = createTextView(activity, i.toString(), 0)\n                            val lp = FlexboxLayout.LayoutParams(100, 100)\n                            lp.flexShrink = 0f\n                            textView.layoutParams = lp\n                            flexboxLayout.addView(textView)\n                        }\n                    }\n                })\n        assertThat(flexboxLayout.childCount, `is`(50))\n        assertThat(flexboxLayout.flexLines.size, `is`(3))\n    }\n\n    @Throws(Throwable::class)\n    private fun createFlexboxLayout(@LayoutRes activityLayoutResId: Int,\n                                    configuration: Configuration = Configuration.EMPTY): FlexboxLayout {\n        val activity = activityRule.activity\n        activityRule.runOnUiThread {\n            activity.setContentView(activityLayoutResId)\n            val flexboxLayout = activity.findViewById<FlexboxLayout>(R.id.flexbox_layout)\n            configuration.apply(flexboxLayout)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        return activity.findViewById<View>(R.id.flexbox_layout) as FlexboxLayout\n    }\n\n    private fun createTextView(context: Context, text: String, order: Int): TextView {\n        val textView = TextView(context)\n        textView.text = text\n        val lp = FlexboxLayout.LayoutParams(\n                ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT)\n        lp.order = order\n        textView.layoutParams = lp\n        return textView\n    }\n\n    private fun hasWidth(width: Int): ViewAssertion {\n        return matches(object : TypeSafeMatcher<View>() {\n            override fun describeTo(description: Description) {\n                description.appendText(\"expected width: $width\")\n            }\n\n            override fun describeMismatchSafely(item: View, mismatchDescription: Description) {\n                mismatchDescription.appendText(\"actual width: \" + item.width)\n            }\n\n            override fun matchesSafely(item: View) = item.width == width\n        })\n    }\n\n    private fun hasHeight(height: Int): ViewAssertion {\n        return matches(object : TypeSafeMatcher<View>() {\n            override fun describeTo(description: Description) {\n                description.appendText(\"expected height: $height\")\n            }\n\n            override fun describeMismatchSafely(item: View, mismatchDescription: Description) {\n                mismatchDescription.appendText(\"actual height: \" + item.height)\n            }\n\n            override fun matchesSafely(item: View) = item.height == height\n        })\n    }\n\n    private interface Configuration {\n\n        fun apply(flexboxLayout: FlexboxLayout)\n\n        companion object {\n            val EMPTY: Configuration = object : Configuration {\n                override fun apply(flexboxLayout: FlexboxLayout) = Unit\n            }\n        }\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/FlexboxLayoutManagerConfigChangeTest.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.content.Context\nimport android.content.pm.ActivityInfo\nimport android.content.res.Configuration\nimport android.view.ViewGroup\nimport androidx.recyclerview.widget.RecyclerView\nimport androidx.test.InstrumentationRegistry\nimport androidx.test.espresso.Espresso.onView\nimport androidx.test.espresso.ViewAction\nimport androidx.test.espresso.action.*\nimport androidx.test.espresso.matcher.ViewMatchers.withId\nimport androidx.test.filters.FlakyTest\nimport androidx.test.filters.MediumTest\nimport androidx.test.rule.ActivityTestRule\nimport androidx.test.runner.AndroidJUnit4\nimport com.google.android.flexbox.FlexDirection\nimport com.google.android.flexbox.FlexboxLayoutManager\nimport org.hamcrest.Matchers.`is`\nimport org.hamcrest.core.IsNot.not\nimport org.junit.Assert.assertThat\nimport org.junit.Rule\nimport org.junit.Test\nimport org.junit.runner.RunWith\n\n/**\n * Integration tests for [FlexboxLayoutManager] with the Activity that handles configuration\n * changes manually.\n */\n@RunWith(AndroidJUnit4::class)\n@MediumTest\nclass FlexboxLayoutManagerConfigChangeTest {\n\n    @JvmField\n    @Rule\n    var activityRule = ActivityTestRule(ConfigChangeActivity::class.java)\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexLinesDiscardedOnOrientationChange_direction_row() {\n        // Verifies the case that the calculated Flex lines are correctly discarded when a\n        // orientation happens with an Activity that handles configuration changes manually\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            // This test assumes that the screen width and the height are different.\n            recyclerView.layoutParams.height = ViewGroup.LayoutParams.MATCH_PARENT\n            recyclerView.layoutParams.width = ViewGroup.LayoutParams.MATCH_PARENT\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..99) {\n                val lp = createLayoutParams(activity, 90, 65)\n                adapter.addItem(lp)\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        val firstLine = layoutManager.flexLines[0]\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n\n        activityRule.runOnUiThread {\n            val orientation = activity.resources.configuration.orientation\n            if (orientation == Configuration.ORIENTATION_PORTRAIT) {\n                activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE\n            } else {\n                activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        activityRule.runOnUiThread { layoutManager.scrollToPosition(0) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val firstLineAfterRotation = layoutManager.flexLines[0]\n        assertThat(firstLine.mainSize, `is`(not(firstLineAfterRotation.mainSize)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexLinesDiscardedOnOrientationChange_direction_column() {\n        // Verifies the case that the calculated Flex lines are correctly discarded when a\n        // orientation happens with an Activity that handles configuration changes manually\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            // This test assumes that the screen width and the height are different.\n            recyclerView.layoutParams.height = ViewGroup.LayoutParams.MATCH_PARENT\n            recyclerView.layoutParams.width = ViewGroup.LayoutParams.MATCH_PARENT\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..99) {\n                val lp = createLayoutParams(activity, 90, 65)\n                adapter.addItem(lp)\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        val firstLine = layoutManager.flexLines[0]\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n\n        activityRule.runOnUiThread {\n            val orientation = activity.resources.configuration.orientation\n            if (orientation == Configuration.ORIENTATION_PORTRAIT) {\n                activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE\n            } else {\n                activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        activityRule.runOnUiThread { layoutManager.scrollToPosition(0) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val firstLineAfterRotation = layoutManager.flexLines[0]\n        assertThat(firstLine.mainSize, `is`(not(firstLineAfterRotation.mainSize)))\n    }\n\n    /**\n     * Creates a new flex item.\n     *\n     * @param context the context\n     * @param width   in DP\n     * @param height  in DP\n     * @return the created [FlexboxLayoutManager.LayoutParams] instance\n     */\n    private fun createLayoutParams(context: Context, width: Int,\n                                   height: Int): FlexboxLayoutManager.LayoutParams {\n        return FlexboxLayoutManager.LayoutParams(context.dpToPixel(width), context.dpToPixel(height))\n    }\n\n    private fun swipe(from: CoordinatesProvider, to: CoordinatesProvider): ViewAction {\n        return GeneralSwipeAction(Swipe.FAST, from, to, Press.FINGER)\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/FlexboxLayoutManagerTest.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.content.Context\nimport android.content.pm.ActivityInfo\nimport android.content.res.Configuration\nimport android.view.ViewGroup\nimport android.widget.TextView\nimport androidx.core.content.res.ResourcesCompat\nimport androidx.recyclerview.widget.LinearLayoutManager\nimport androidx.recyclerview.widget.RecyclerView\nimport androidx.test.espresso.Espresso.onView\nimport androidx.test.espresso.ViewAction\nimport androidx.test.espresso.action.CoordinatesProvider\nimport androidx.test.espresso.action.GeneralLocation\nimport androidx.test.espresso.action.GeneralSwipeAction\nimport androidx.test.espresso.action.Press\nimport androidx.test.espresso.action.Swipe\nimport androidx.test.espresso.matcher.ViewMatchers.withId\nimport androidx.test.ext.junit.runners.AndroidJUnit4\nimport androidx.test.filters.FlakyTest\nimport androidx.test.filters.MediumTest\nimport androidx.test.platform.app.InstrumentationRegistry\nimport androidx.test.rule.ActivityTestRule\nimport com.google.android.flexbox.AlignItems\nimport com.google.android.flexbox.AlignSelf\nimport com.google.android.flexbox.FlexDirection\nimport com.google.android.flexbox.FlexWrap\nimport com.google.android.flexbox.FlexboxItemDecoration\nimport com.google.android.flexbox.FlexboxItemDecoration.HORIZONTAL\nimport com.google.android.flexbox.FlexboxItemDecoration.VERTICAL\nimport com.google.android.flexbox.FlexboxLayoutManager\nimport com.google.android.flexbox.JustifyContent\nimport com.google.android.flexbox.test.IsEqualAllowingError.Companion.isEqualAllowingError\nimport org.hamcrest.Matchers.`is`\nimport org.hamcrest.Matchers.instanceOf\nimport org.hamcrest.Matchers.lessThan\nimport org.hamcrest.Matchers.notNullValue\nimport org.hamcrest.core.IsNot.not\nimport org.junit.Assert.assertThat\nimport org.junit.Assert.assertTrue\nimport org.junit.Rule\nimport org.junit.Test\nimport org.junit.runner.RunWith\n\n/**\n * Integration tests for [FlexboxLayoutManager].\n */\n@RunWith(AndroidJUnit4::class)\n@MediumTest\nclass FlexboxLayoutManagerTest {\n\n    @JvmField\n    @Rule\n    var activityRule = ActivityTestRule(FlexboxTestActivity::class.java)\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testLoadFromXml() {\n        val activity = activityRule.activity\n        activityRule.runOnUiThread { activity.setContentView(R.layout.recyclerview_reverse) }\n        val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n        val layoutManager = recyclerView.layoutManager\n        assertThat(recyclerView, `is`(notNullValue()))\n        assertThat(layoutManager, `is`(instanceOf<Any>(FlexboxLayoutManager::class.java)))\n        val flexboxLayoutManager = layoutManager as FlexboxLayoutManager\n        assertThat(flexboxLayoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(flexboxLayoutManager.flexWrap, `is`(FlexWrap.WRAP))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChangeAttributesFromCode() {\n        val activity = activityRule.activity\n        activityRule.runOnUiThread { activity.setContentView(R.layout.recyclerview_reverse) }\n        val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n        val layoutManager = recyclerView.layoutManager\n        assertThat(recyclerView, `is`(notNullValue()))\n        assertThat(layoutManager, `is`(instanceOf<Any>(FlexboxLayoutManager::class.java)))\n        val flexboxLayoutManager = layoutManager as FlexboxLayoutManager\n        assertThat(flexboxLayoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(flexboxLayoutManager.flexWrap, `is`(FlexWrap.WRAP))\n\n        flexboxLayoutManager.flexDirection = FlexDirection.COLUMN\n        flexboxLayoutManager.flexWrap = FlexWrap.NOWRAP\n        flexboxLayoutManager.justifyContent = JustifyContent.CENTER\n        flexboxLayoutManager.alignItems = AlignItems.FLEX_END\n        assertThat(flexboxLayoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(flexboxLayoutManager.flexWrap, `is`(FlexWrap.NOWRAP))\n        assertThat(flexboxLayoutManager.justifyContent, `is`(JustifyContent.CENTER))\n        assertThat(flexboxLayoutManager.alignItems, `is`(AlignItems.FLEX_END))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAddViewHolders_direction_row_not_wrapped() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            adapter.addItem(createLayoutParams(activity, 120, 80))\n            adapter.addItem(createLayoutParams(activity, 120, 80))\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(layoutManager.flexWrap, `is`(FlexWrap.WRAP))\n        // Only 2 items are added and all items should be attached (visible). So both\n        // getChildCount and getFlexItemCount(including detached items) should return the same value\n        assertThat(layoutManager.flexItemCount, `is`(2))\n        assertThat(layoutManager.childCount, `is`(2))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAddViewHolders_direction_row_wrapped() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            adapter.addItem(createLayoutParams(activity, 120, 80))\n            adapter.addItem(createLayoutParams(activity, 120, 80))\n            adapter.addItem(createLayoutParams(activity, 120, 80))\n            adapter.addItem(createLayoutParams(activity, 120, 80))\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // 4 items are added and all items should be attached (visible). So both\n        // getChildCount and getFlexItemCount(including detached items) should return the same value\n        assertThat(layoutManager.flexItemCount, `is`(4))\n        assertThat(layoutManager.childCount, `is`(4))\n        assertThat(layoutManager.flexLines.size, `is`(2))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAddViewHolders_direction_row_partOfItems_detached() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            // RecyclerView width: 320, height: 240.\n            // Computed FlexContainer width: 320, height: 450\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // In total 9 items are added but the seventh item and the items follow aren't attached\n        // (invisible) so are not included in the count of of the getChildCount.\n        assertThat(layoutManager.flexItemCount, `is`(9))\n        assertThat(layoutManager.childCount, `is`(6))\n\n        // At first only the visible area of the flex lines are calculated\n        assertThat(layoutManager.flexLines.size, `is`(3))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAddViewHolders_direction_row_scrollVertically() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            adapter.addItem(createLayoutParams(activity, 150, 90))\n            // RecyclerView width: 320, height: 240.\n            // Computed FlexContainer width: 320, height: 450\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // In total 9 items are added but the seventh item and the items follow aren't attached\n        // (invisible) so are not included in the count of of the getChildCount.\n        assertThat(layoutManager.flexItemCount, `is`(9))\n        assertThat(layoutManager.childCount, `is`(6))\n        // At first only the visible area of the flex lines are calculated\n        assertThat(layoutManager.flexLines.size, `is`(3))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        assertThat(layoutManager.flexItemCount, `is`(9))\n        // The RecyclerView is swiped to top until it reaches the bottom of the view.\n        // The number of the visible views should be 5\n        assertThat(layoutManager.childCount, `is`(5))\n        // Since the RecyclerView is swiped to the bottom, all flex lines should be calculated\n        // by now\n        assertThat(layoutManager.flexLines.size, `is`(5))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexGrow() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 150, 130)\n            lp1.flexGrow = 1.0f\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 150, 130)\n            lp2.flexGrow = 1.0f\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 150, 130)\n            lp3.flexGrow = 1.0f\n            adapter.addItem(lp3)\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // The flexGrow parameters for all LayoutParams are set to 1.0, expecting each child to\n        // fill the horizontal remaining space\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(2))\n        assertThat(layoutManager.getChildAt(0)!!.width, isEqualAllowingError(activity.dpToPixel(160)))\n        assertThat(layoutManager.getChildAt(1)!!.width, isEqualAllowingError(activity.dpToPixel(160)))\n        assertThat(layoutManager.getChildAt(2)!!.width, isEqualAllowingError(activity.dpToPixel(320)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAddViewHolders_direction_column_partOfItems_detached() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            // RecyclerView width: 320, height: 240.\n            // Computed FlexContainer width: 450, height: 240\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // In total 9 items are added but the seventh item and the items after aren't attached\n        // (invisible) so are not included in the count of of the getChildCount.\n        assertThat(layoutManager.flexItemCount, `is`(9))\n        assertThat(layoutManager.childCount, `is`(6))\n\n        // At first only the visible area of the flex lines are calculated\n        assertThat(layoutManager.flexLines.size, `is`(3))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAddViewHolders_direction_column_scrollHorizontally() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n            adapter.addItem(createLayoutParams(activity, 120, 100))\n\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            // RecyclerView width: 320, height: 240.\n            // Computed FlexContainer width: 500, height: 240\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // In total 9 items are added but the seventh item and the items follow aren't attached\n        // (invisible) so are not included in the count of of the getChildCount.\n        assertThat(layoutManager.flexItemCount, `is`(9))\n        assertThat(layoutManager.childCount, `is`(6))\n        // At first only the visible area of the flex lines are calculated\n        assertThat(layoutManager.flexLines.size, `is`(3))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        assertThat(layoutManager.flexItemCount, `is`(9))\n        // The RecyclerView is swiped to top until it reaches the right edge of the view.\n        // The number of the visible views should be 5\n        assertThat(layoutManager.childCount, `is`(5))\n        // Since the RecyclerView is swiped to the bottom, all flex lines should be calculated\n        // by now\n        assertThat(layoutManager.flexLines.size, `is`(5))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexStart_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.justifyContent = JustifyContent.FLEX_START\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.FLEX_START))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(0)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(150)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexEnd_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.justifyContent = JustifyContent.FLEX_END\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.FLEX_END))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(170)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(220)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(220)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(320)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_center_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.justifyContent = JustifyContent.CENTER\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.CENTER))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(85)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(235)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.justifyContent = JustifyContent.SPACE_AROUND\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(28)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(78)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(242)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(292)))\n    }\n\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceEvenly_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.justifyContent = JustifyContent.SPACE_EVENLY\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_EVENLY))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(43)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(93)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(228)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(278)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.justifyContent = JustifyContent.SPACE_BETWEEN\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(0)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(320)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexStart_direction_rowReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.ROW_REVERSE\n            layoutManager.justifyContent = JustifyContent.FLEX_START\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.FLEX_START))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(320)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(220)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(170)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(220)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexEnd_direction_rowReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.ROW_REVERSE\n            layoutManager.justifyContent = JustifyContent.FLEX_END\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.FLEX_END))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(150)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(0)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(50)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_center_direction_rowReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.ROW_REVERSE\n            layoutManager.justifyContent = JustifyContent.CENTER\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.CENTER))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(235)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(85)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(135)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_direction_rowReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.ROW_REVERSE\n            layoutManager.justifyContent = JustifyContent.SPACE_AROUND\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(242)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(292)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(28)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(78)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceEvenly_direction_rowReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.ROW_REVERSE\n            layoutManager.justifyContent = JustifyContent.SPACE_EVENLY\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_EVENLY))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(228)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(278)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(43)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(93)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_direction_rowReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 50, 100)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.ROW_REVERSE\n            layoutManager.justifyContent = JustifyContent.SPACE_BETWEEN\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.left, isEqualAllowingError(activity.dpToPixel(270)))\n        assertThat(view0.right, isEqualAllowingError(activity.dpToPixel(320)))\n        assertThat(view1.left, isEqualAllowingError(activity.dpToPixel(135)))\n        assertThat(view1.right, isEqualAllowingError(activity.dpToPixel(185)))\n        assertThat(view2.left, isEqualAllowingError(activity.dpToPixel(0)))\n        assertThat(view2.right, isEqualAllowingError(activity.dpToPixel(50)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexStart_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.justifyContent = JustifyContent.FLEX_START\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.FLEX_START))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(0)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(150)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexEnd_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.justifyContent = JustifyContent.FLEX_END\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.FLEX_END))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(90)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(140)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(140)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(190)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(190)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(240)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_center_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.justifyContent = JustifyContent.CENTER\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.CENTER))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(45)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(195)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.justifyContent = JustifyContent.SPACE_AROUND\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(15)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(65)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(175)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(225)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceEvenly_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.justifyContent = JustifyContent.SPACE_EVENLY\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_EVENLY))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(23)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(73)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(167)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(217)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.justifyContent = JustifyContent.SPACE_BETWEEN\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(0)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(190)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(240)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexStart_direction_columnReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN_REVERSE\n            layoutManager.justifyContent = JustifyContent.FLEX_START\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.FLEX_START))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(190)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(240)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(140)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(190)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(90)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(140)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_flexEnd_direction_columnReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN_REVERSE\n            layoutManager.justifyContent = JustifyContent.FLEX_END\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.FLEX_END))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(150)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(0)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(50)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_center_direction_columnReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN_REVERSE\n            layoutManager.justifyContent = JustifyContent.CENTER\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.CENTER))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(195)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(45)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(95)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceAround_direction_columnReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN_REVERSE\n            layoutManager.justifyContent = JustifyContent.SPACE_AROUND\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_AROUND))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(175)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(225)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(15)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(65)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceEvenly_direction_columnReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN_REVERSE\n            layoutManager.justifyContent = JustifyContent.SPACE_EVENLY\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_EVENLY))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(167)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(217)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(23)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(73)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testJustifyContent_spaceBetween_direction_columnReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 50)\n            adapter.addItem(lp3)\n            layoutManager.flexDirection = FlexDirection.COLUMN_REVERSE\n            layoutManager.justifyContent = JustifyContent.SPACE_BETWEEN\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN_REVERSE))\n        assertThat(layoutManager.justifyContent, `is`(JustifyContent.SPACE_BETWEEN))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        val view0 = layoutManager.getChildAt(0)!!\n        val view1 = layoutManager.getChildAt(1)!!\n        val view2 = layoutManager.getChildAt(2)!!\n        assertThat(view0.top, isEqualAllowingError(activity.dpToPixel(190)))\n        assertThat(view0.bottom, isEqualAllowingError(activity.dpToPixel(240)))\n        assertThat(view1.top, isEqualAllowingError(activity.dpToPixel(95)))\n        assertThat(view1.bottom, isEqualAllowingError(activity.dpToPixel(145)))\n        assertThat(view2.top, isEqualAllowingError(activity.dpToPixel(0)))\n        assertThat(view2.bottom, isEqualAllowingError(activity.dpToPixel(50)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testLargeItem_scrollFast_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..199) {\n                val lp = createLayoutParams(activity, 100, 50)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(layoutManager.flexItemCount, `is`(200))\n        // Only the visible items\n        assertThat(layoutManager.childCount, `is`(not(200)))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        // Should be scrolled to the bottom by now\n        assertThat(layoutManager.flexItemCount, `is`(200))\n        // Only the visible items\n        assertThat(layoutManager.childCount, `is`(not(200)))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        // Should be scrolled to the top\n        assertThat(layoutManager.flexItemCount, `is`(200))\n        // Only the visible items\n        assertThat(layoutManager.childCount, `is`(not(200)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testLargeItem_scrollFast_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..199) {\n                val lp = createLayoutParams(activity, 70, 80)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.flexItemCount, `is`(200))\n        // Only the visible items\n        assertThat(layoutManager.childCount, `is`(not(200)))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n\n        // Should be scrolled to the right edge by now\n        assertThat(layoutManager.flexItemCount, `is`(200))\n        // Only the visible items\n        assertThat(layoutManager.childCount, `is`(not(200)))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        // Should be scrolled to the left edge by now\n        assertThat(layoutManager.flexItemCount, `is`(200))\n        // Only the visible items\n        assertThat(layoutManager.childCount, `is`(not(200)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_stretch_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.alignItems = AlignItems.STRETCH\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 70, 80)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 70, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 70, 30)\n            adapter.addItem(lp3)\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(layoutManager.alignItems, `is`(AlignItems.STRETCH))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        // Verify all items heights are stretched\n        assertThat(layoutManager.getChildAt(0)!!.height, isEqualAllowingError(activity.dpToPixel(80)))\n        assertThat(layoutManager.getChildAt(1)!!.height, isEqualAllowingError(activity.dpToPixel(80)))\n        assertThat(layoutManager.getChildAt(2)!!.height, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignItems_stretch_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.alignItems = AlignItems.STRETCH\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 80, 70)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 70)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 30, 70)\n            adapter.addItem(lp3)\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.alignItems, `is`(AlignItems.STRETCH))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        // Verify all items widths are stretched\n        assertThat(layoutManager.getChildAt(0)!!.width, isEqualAllowingError(activity.dpToPixel(80)))\n        assertThat(layoutManager.getChildAt(1)!!.width, isEqualAllowingError(activity.dpToPixel(80)))\n        assertThat(layoutManager.getChildAt(2)!!.width, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignSelf_stretch_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.alignItems = AlignItems.FLEX_START\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 70, 80)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 70, 50)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 70, 30)\n            lp3.alignSelf = AlignSelf.STRETCH\n            adapter.addItem(lp3)\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(layoutManager.alignItems, `is`(AlignItems.FLEX_START))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        // Verify the item whose align self is set to stretch is stretched\n        assertThat(layoutManager.getChildAt(0)!!.height, isEqualAllowingError(activity.dpToPixel(80)))\n        assertThat(layoutManager.getChildAt(1)!!.height, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(layoutManager.getChildAt(2)!!.height, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testAlignSelf_stretch_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.alignItems = AlignItems.FLEX_START\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 80, 70)\n            adapter.addItem(lp1)\n            val lp2 = createLayoutParams(activity, 50, 70)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 30, 70)\n            lp3.alignSelf = AlignSelf.STRETCH\n            adapter.addItem(lp3)\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.alignItems, `is`(AlignItems.FLEX_START))\n        assertThat(layoutManager.flexItemCount, `is`(3))\n        assertThat(layoutManager.flexLines.size, `is`(1))\n        // Verify the item whose align self is set to stretch is stretched\n        assertThat(layoutManager.getChildAt(0)!!.width, isEqualAllowingError(activity.dpToPixel(80)))\n        assertThat(layoutManager.getChildAt(1)!!.width, isEqualAllowingError(activity.dpToPixel(50)))\n        assertThat(layoutManager.getChildAt(2)!!.width, isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testStretchViews_from_middle_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.alignItems = AlignItems.STRETCH\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 70, 80)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(layoutManager.alignItems, `is`(AlignItems.STRETCH))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        activityRule.runOnUiThread {\n            layoutManager.alignItems = AlignItems.STRETCH\n            val lp = createLayoutParams(activity, 70, 20)\n            // Add an item whose height is less than the other items.\n            // But with alignItems set to stretch, the height of the item should be stretched\n            adapter.addItem(lp)\n            adapter.notifyDataSetChanged()\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.getChildAt(layoutManager.childCount - 1)!!.height,\n                isEqualAllowingError(activity.dpToPixel(80)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testStretchViews_from_middle_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.alignItems = AlignItems.STRETCH\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 70, 50)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.alignItems, `is`(AlignItems.STRETCH))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_RIGHT,\n                GeneralLocation.TOP_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_RIGHT,\n                GeneralLocation.TOP_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_RIGHT,\n                GeneralLocation.TOP_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_RIGHT,\n                GeneralLocation.TOP_LEFT))\n        activityRule.runOnUiThread {\n            layoutManager.alignItems = AlignItems.STRETCH\n            val lp = createLayoutParams(activity, 20, 50)\n            // Add an item whose width is less than the other items.\n            // But with alignItems set to stretch, the width of the item should be stretched\n            adapter.addItem(lp)\n            adapter.notifyDataSetChanged()\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.getChildAt(layoutManager.childCount - 1)!!.width,\n                isEqualAllowingError(activity.dpToPixel(70)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToTop_middleItem_as_anchorPosition() {\n        // There was an issue that the anchor position was based on the first item in the first\n        // visible flex line when scrolling to top. But the anchor position should be based on the\n        // flex line position (view which has the minimum top position in the same flex line)\n        // This test verifies the issue is fixed.\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val positionInSecondLine = 6\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.alignItems = AlignItems.FLEX_START\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..49) {\n                var lp = createLayoutParams(activity, 70, 80)\n                if (i == positionInSecondLine) {\n                    // Change the height from other items in the second line, not the first item\n                    // in the second line\n                    lp = createLayoutParams(activity, 70, 130)\n                }\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // Each line has 4 (320 / 70) flex items and 12 (50 / 4) lines in total\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        // By this moment reached to the bottom\n\n        // Now scrolling to the top to see if the views in the first flex line is correctly placed\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n\n        assertThat(layoutManager.getChildAt(positionInSecondLine)!!.bottom,\n                isEqualAllowingError(activity.dpToPixel(210))) // 80 + 130\n        // Verify that the view in the same line's cross axis position is correct\n        assertThat(layoutManager.getChildAt(positionInSecondLine - 1)!!.bottom,\n                isEqualAllowingError(activity.dpToPixel(160))) // 80 + 80\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToLeft_middleItem_as_anchorPosition() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val positionInSecondLine = 6\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.alignItems = AlignItems.FLEX_START\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..49) {\n                var lp = createLayoutParams(activity, 80, 50)\n                if (i == positionInSecondLine) {\n                    // Change the width from other items in the second line, not the first item\n                    // in the second line\n                    lp = createLayoutParams(activity, 130, 50)\n                }\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // Each line has 4 (240 / 50) flex items and 12 (50 / 4) lines in total\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        // By this moment reached to the right edge\n\n        // Now scrolling to the left to see if the views in the first flex line is correctly placed\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n\n        assertThat(layoutManager.getChildAt(positionInSecondLine)!!.right,\n                isEqualAllowingError(activity.dpToPixel(210))) // 80 + 130\n        // Verify that the view in the same line's cross axis position is correct\n        assertThat(layoutManager.getChildAt(positionInSecondLine - 1)!!.right,\n                isEqualAllowingError(activity.dpToPixel(160))) // 80 + 80\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToBottom_middleItem_as_anchorPosition() {\n        // There was an issue that the anchor position was based on the last item in the last\n        // visible flex line when scrolling to bottom. But the anchor position should be based on\n        // the flex line position (view which has the maximum bottom position in the same flex line)\n        // This test verifies the issue is fixed.\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val positionInSecondBottomLine = 45\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..49) {\n                var lp = createLayoutParams(activity, 70, 80)\n                if (i == positionInSecondBottomLine) {\n                    // Change the height from other items in the second bottom line\n                    lp = createLayoutParams(activity, 70, 130)\n                }\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // Each line has 4 (320 / 70) flex items and 12 (50 / 4) lines in total\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        // By this moment reached to the bottom\n\n        // 4 comes from the number of flex items - positionInSecondBottomLine\n        val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n        val anchorView = layoutManager.getChildAt(layoutManager.childCount - 4)\n        assertThat(recyclerView.bottom - anchorView!!.top,\n                isEqualAllowingError(activity.dpToPixel(210))) // 80 + 130\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToTop_direction_rowReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW_REVERSE\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 70, 80)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // Each line has 4 (320 / 70) flex items and 12 (50 / 4) lines in total\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        // By this moment reached to the bottom\n\n        // Now scrolling to the top to see if the views in the first flex line is correctly placed\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n\n        assertThat((layoutManager.getChildAt(0) as TextView).text.toString(), `is`(\"1\"))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexGrow_only_oneItem_has_positive_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..3) {\n                val lp = createLayoutParams(activity, 100, 80)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 3 items\n            // Flex line 2: 1 item\n            // Give the second item in the first line a positive flex grow\n            adapter.getItemAt(0).setHeight(activity.dpToPixel(140))\n            adapter.getItemAt(1).flexGrow = 1.0f\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        // Verify the vertical position (cross size) of the second line is correctly positioned\n        assertThat(layoutManager.getChildAt(3)!!.top, isEqualAllowingError(activity.dpToPixel(140)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFlexGrow_only_oneItem_has_positive_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..3) {\n                val lp = createLayoutParams(activity, 70, 70)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 3 items\n            // Flex line 2: 1 item\n            // Give the second item in the first line a positive flex grow\n            adapter.getItemAt(0).setWidth(activity.dpToPixel(120))\n            adapter.getItemAt(1).flexGrow = 1.0f\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        // Verify the horizontal position (cross size) of the second line is correctly positioned\n        assertThat(layoutManager.getChildAt(3)!!.left, isEqualAllowingError(activity.dpToPixel(120)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFirstReferenceView_middleOf_line_used_as_anchor() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.alignItems = AlignItems.FLEX_END\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp1 = createLayoutParams(activity, 100, 80)\n            adapter.addItem(lp1)\n            // The second view in the first line has the maximum height in the same line\n            val lp2 = createLayoutParams(activity, 100, 180)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 80)\n            adapter.addItem(lp3)\n            for (i in 0..29) {\n                val lp = createLayoutParams(activity, 100, 80)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        // By this moment reached to the bottom\n\n        // Now scrolling to the top to see if the views in the first flex line is correctly placed\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n\n        // The top coordinate of the first view should be the height of the second view minus the\n        // height of the first view (180 - 80)\n        assertThat(layoutManager.getChildAt(0)!!.top, isEqualAllowingError(activity.dpToPixel(100)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testLastReferenceView_middleOf_line_used_as_anchor() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.alignItems = AlignItems.FLEX_START\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..29) {\n                val lp = createLayoutParams(activity, 100, 80)\n                adapter.addItem(lp)\n            }\n            val lp1 = createLayoutParams(activity, 100, 80)\n            adapter.addItem(lp1)\n            // The second view in the last line has the maximum height in the same line\n            val lp2 = createLayoutParams(activity, 100, 180)\n            adapter.addItem(lp2)\n            val lp3 = createLayoutParams(activity, 100, 80)\n            adapter.addItem(lp3)\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        // By this moment reached to the bottom\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n\n        // The bottom coordinate of the first view in the last line should be the height of the\n        // second view in the last line minus the height of the first view in the last line\n        // (180 - 80)\n        assertThat(layoutManager.getChildAt(layoutManager.childCount - 2)!!.bottom\n                - layoutManager.getChildAt(layoutManager.childCount - 3)!!.bottom,\n                isEqualAllowingError(activity.dpToPixel(100)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testRotateScreen_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.alignItems = AlignItems.STRETCH\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..29) {\n                val lp = createLayoutParams(activity, 100, 100)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.CENTER))\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        val anchorView = layoutManager.getChildAt(0)\n        val offset = anchorView!!.top\n        assertTrue(offset < 0)\n\n        activityRule.runOnUiThread {\n            val orientation = activity.resources.configuration.orientation\n            if (orientation == Configuration.ORIENTATION_PORTRAIT) {\n                activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE\n            } else {\n                activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // Verify that offset position is preserved for the first visible view after the rotation\n        val anchorAfterRotate = layoutManager.getChildAt(0)\n        assertTrue(anchorAfterRotate!!.top < 0)\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testRotateScreen_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.alignItems = AlignItems.STRETCH\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..29) {\n                val lp = createLayoutParams(activity, 100, 100)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER))\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        val anchorView = layoutManager.getChildAt(0)\n        val offset = anchorView!!.left\n        assertTrue(offset < 0)\n\n        activityRule.runOnUiThread {\n            val orientation = activity.resources.configuration.orientation\n            if (orientation == Configuration.ORIENTATION_PORTRAIT) {\n                activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE\n            } else {\n                activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // Verify that offset position is preserved for the first visible view after the rotation\n        val anchorAfterRotate = layoutManager.getChildAt(0)\n        assertTrue(anchorAfterRotate!!.left < 0)\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDecoration_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val drawable = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        val itemDecoration = FlexboxItemDecoration(activity)\n        itemDecoration.setDrawable(drawable)\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.addItemDecoration(itemDecoration)\n            recyclerView.adapter = adapter\n\n            for (i in 0..9) {\n                val lp = createLayoutParams(activity, 90, 100)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        var view2 = layoutManager.getChildAt(1)\n        // 90 (view width) + 10 (divider width)\n        assertThat(view2!!.left, isEqualAllowingError(activity.dpToPixel(100)))\n        var view3 = layoutManager.getChildAt(2)\n        // 90 (view width) + 10 (divider width) + 90(view width) + 10 (divider width)\n        assertThat(view3!!.left, isEqualAllowingError(activity.dpToPixel(200)))\n        var view4 = layoutManager.getChildAt(3)\n        // 100 (view height) + 15 (divider height)\n        assertThat(view4!!.top, isEqualAllowingError(activity.dpToPixel(115)))\n        var view7 = layoutManager.getChildAt(6)\n        // 100 (view height) + 15 (divider height) + 100 (view height) + 15 (divider height)\n        assertThat(view7!!.top, isEqualAllowingError(activity.dpToPixel(230)))\n\n        activityRule.runOnUiThread {\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.removeItemDecoration(itemDecoration)\n            itemDecoration.setOrientation(HORIZONTAL)\n            recyclerView.addItemDecoration(itemDecoration)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        view2 = layoutManager.getChildAt(1)\n        // 90 (view width)\n        assertThat(view2!!.left, isEqualAllowingError(activity.dpToPixel(90)))\n        view3 = layoutManager.getChildAt(2)\n        // 90 (view width) + 90(view width)\n        assertThat(view3!!.left, isEqualAllowingError(activity.dpToPixel(180)))\n        view4 = layoutManager.getChildAt(3)\n        // 100 (view height) + 15 (divider height)\n        assertThat(view4!!.top, isEqualAllowingError(activity.dpToPixel(115)))\n        view7 = layoutManager.getChildAt(6)\n        // 100 (view height) + 15 (divider height) + 100 (view height) + 15 (divider height)\n        assertThat(view7!!.top, isEqualAllowingError(activity.dpToPixel(230)))\n\n        activityRule.runOnUiThread {\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.removeItemDecoration(itemDecoration)\n            itemDecoration.setOrientation(VERTICAL)\n            recyclerView.addItemDecoration(itemDecoration)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        view2 = layoutManager.getChildAt(1)\n        // 90 (view width) + 10 (divider width)\n        assertThat(view2!!.left, isEqualAllowingError(activity.dpToPixel(100)))\n        view3 = layoutManager.getChildAt(2)\n        // 90 (view width) + 10 (divider width) + 90(view width) + 10 (divider width)\n        assertThat(view3!!.left, isEqualAllowingError(activity.dpToPixel(200)))\n        view4 = layoutManager.getChildAt(3)\n        // 100 (view height)\n        assertThat(view4!!.top, isEqualAllowingError(activity.dpToPixel(100)))\n        view7 = layoutManager.getChildAt(6)\n        // 100 (view height) + 100 (view height)\n        assertThat(view7!!.top, isEqualAllowingError(activity.dpToPixel(200)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDecoration_direction_rowReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val drawable = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        val itemDecoration = FlexboxItemDecoration(activity)\n        itemDecoration.setDrawable(drawable)\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW_REVERSE\n            recyclerView.layoutManager = layoutManager\n            recyclerView.addItemDecoration(itemDecoration)\n            recyclerView.adapter = adapter\n\n            for (i in 0..9) {\n                val lp = createLayoutParams(activity, 90, 100)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW_REVERSE))\n        var view1 = layoutManager.getChildAt(0)\n        var view2 = layoutManager.getChildAt(1)\n        // 90 (view width) + 10 (divider width)\n        assertThat(view1!!.right - view2!!.right, isEqualAllowingError(activity.dpToPixel(100)))\n        var view3 = layoutManager.getChildAt(2)\n        // 90 (view width) + 10 (divider width) + 90(view width) + 10 (divider width)\n        assertThat(view1.right - view3!!.right, isEqualAllowingError(activity.dpToPixel(200)))\n        var view4 = layoutManager.getChildAt(3)\n        // 100 (view height) + 15 (divider height)\n        assertThat(view4!!.top, isEqualAllowingError(activity.dpToPixel(115)))\n        var view7 = layoutManager.getChildAt(6)\n        // 100 (view height) + 15 (divider height) + 100 (view height) + 15 (divider height)\n        assertThat(view7!!.top, isEqualAllowingError(activity.dpToPixel(230)))\n\n        activityRule.runOnUiThread {\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.removeItemDecoration(itemDecoration)\n            itemDecoration.setOrientation(HORIZONTAL)\n            recyclerView.addItemDecoration(itemDecoration)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        view1 = layoutManager.getChildAt(0)\n        view2 = layoutManager.getChildAt(1)\n        // 90 (view width)\n        assertThat(view1!!.right - view2!!.right, isEqualAllowingError(activity.dpToPixel(90)))\n        view3 = layoutManager.getChildAt(2)\n        // 90 (view width) + 90(view width)\n        assertThat(view1.right - view3!!.right, isEqualAllowingError(activity.dpToPixel(180)))\n        view4 = layoutManager.getChildAt(3)\n        // 100 (view height) + 15 (divider height)\n        assertThat(view4!!.top, isEqualAllowingError(activity.dpToPixel(115)))\n        view7 = layoutManager.getChildAt(6)\n        // 100 (view height) + 15 (divider height) + 100 (view height) + 15 (divider height)\n        assertThat(view7!!.top, isEqualAllowingError(activity.dpToPixel(230)))\n\n        activityRule.runOnUiThread {\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.removeItemDecoration(itemDecoration)\n            itemDecoration.setOrientation(VERTICAL)\n            recyclerView.addItemDecoration(itemDecoration)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        view1 = layoutManager.getChildAt(0)\n        view2 = layoutManager.getChildAt(1)\n        // 90 (view width) + 10 (divider width)\n        assertThat(view1!!.right - view2!!.right,\n                isEqualAllowingError(activity.dpToPixel(100)))\n        view3 = layoutManager.getChildAt(2)\n        // 90 (view width) + 10 (divider width) + 90(view width) + 10 (divider width)\n        assertThat(view1.right - view3!!.right,\n                isEqualAllowingError(activity.dpToPixel(200)))\n        view4 = layoutManager.getChildAt(3)\n        // 100 (view height)\n        assertThat(view4!!.top, isEqualAllowingError(activity.dpToPixel(100)))\n        view7 = layoutManager.getChildAt(6)\n        // 100 (view height) + 100 (view height)\n        assertThat(view7!!.top, isEqualAllowingError(activity.dpToPixel(200)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDecoration_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val drawable = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        val itemDecoration = FlexboxItemDecoration(activity)\n        itemDecoration.setDrawable(drawable)\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.addItemDecoration(itemDecoration)\n            recyclerView.adapter = adapter\n\n            for (i in 0..9) {\n                val lp = createLayoutParams(activity, 90, 65)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        var view2 = layoutManager.getChildAt(1)\n        // 65 (view height) + 15 (divider height)\n        assertThat(view2!!.top, isEqualAllowingError(activity.dpToPixel(80)))\n        var view3 = layoutManager.getChildAt(2)\n        // 65 (view height) + 15 (divider height) + 65 (view height) + 15 (divider height)\n        assertThat(view3!!.top, isEqualAllowingError(activity.dpToPixel(160)))\n        var view4 = layoutManager.getChildAt(3)\n        // 90 (view width) + 10 (divider width)\n        assertThat(view4!!.left, isEqualAllowingError(activity.dpToPixel(100)))\n        var view7 = layoutManager.getChildAt(6)\n        // 90 (view width) + 10 (divider width) + 90 (view width) + 10 (divider width)\n        assertThat(view7!!.left, isEqualAllowingError(activity.dpToPixel(200)))\n\n        activityRule.runOnUiThread {\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.removeItemDecoration(itemDecoration)\n            itemDecoration.setOrientation(HORIZONTAL)\n            recyclerView.addItemDecoration(itemDecoration)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        view2 = layoutManager.getChildAt(1)\n        // 65 (view height) + 15 (divider height)\n        assertThat(view2!!.top, isEqualAllowingError(activity.dpToPixel(80)))\n        view3 = layoutManager.getChildAt(2)\n        // 65 (view height) + 15 (divider height) + 65 (view height) + 15 (divider height)\n        assertThat(view3!!.top, isEqualAllowingError(activity.dpToPixel(160)))\n        view4 = layoutManager.getChildAt(3)\n        // 90 (view width)\n        assertThat(view4!!.left, isEqualAllowingError(activity.dpToPixel(90)))\n        view7 = layoutManager.getChildAt(6)\n        // 90 (view width) + 90 (view width)\n        assertThat(view7!!.left, isEqualAllowingError(activity.dpToPixel(180)))\n\n        activityRule.runOnUiThread {\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.removeItemDecoration(itemDecoration)\n            itemDecoration.setOrientation(VERTICAL)\n            recyclerView.addItemDecoration(itemDecoration)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        view2 = layoutManager.getChildAt(1)\n        // 65 (view height)\n        assertThat(view2!!.top, isEqualAllowingError(activity.dpToPixel(65)))\n        view3 = layoutManager.getChildAt(2)\n        // 65 (view height) + 65 (view height)\n        assertThat(view3!!.top, isEqualAllowingError(activity.dpToPixel(130)))\n        view4 = layoutManager.getChildAt(3)\n        // 90 (view width) + 10 (divider width)\n        assertThat(view4!!.left, isEqualAllowingError(activity.dpToPixel(100)))\n        view7 = layoutManager.getChildAt(6)\n        // 90 (view width) + 10 (divider width) + 90 (view width) + 10 (divider width)\n        assertThat(view7!!.left, isEqualAllowingError(activity.dpToPixel(200)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDecoration_direction_columnReverse() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val drawable = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        val itemDecoration = FlexboxItemDecoration(activity)\n        itemDecoration.setDrawable(drawable)\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN_REVERSE\n            recyclerView.layoutManager = layoutManager\n            recyclerView.addItemDecoration(itemDecoration)\n            recyclerView.adapter = adapter\n\n            for (i in 0..9) {\n                val lp = createLayoutParams(activity, 90, 65)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN_REVERSE))\n        var view1 = layoutManager.getChildAt(0)\n        var view2 = layoutManager.getChildAt(1)\n        // 65 (view height) + 15 (divider height)\n        assertThat(view1!!.top - view2!!.top, isEqualAllowingError(activity.dpToPixel(80)))\n        var view3 = layoutManager.getChildAt(2)\n        // 65 (view height) + 15 (divider height) + 65 (view height) + 15 (divider height)\n        assertThat(view1.top - view3!!.top, isEqualAllowingError(activity.dpToPixel(160)))\n        var view4 = layoutManager.getChildAt(3)\n        // 90 (view width) + 10 (divider width)\n        assertThat(view4!!.left, isEqualAllowingError(activity.dpToPixel(100)))\n        var view7 = layoutManager.getChildAt(6)\n        // 90 (view width) + 10 (divider width) + 90 (view width) + 10 (divider width)\n        assertThat(view7!!.left, isEqualAllowingError(activity.dpToPixel(200)))\n\n        activityRule.runOnUiThread {\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.removeItemDecoration(itemDecoration)\n            itemDecoration.setOrientation(HORIZONTAL)\n            recyclerView.addItemDecoration(itemDecoration)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        view1 = layoutManager.getChildAt(0)\n        view2 = layoutManager.getChildAt(1)\n        // 65 (view height) + 15 (divider height)\n        assertThat(view1!!.top - view2!!.top, isEqualAllowingError(activity.dpToPixel(80)))\n        view3 = layoutManager.getChildAt(2)\n        // 65 (view height) + 15 (divider height) + 65 (view height) + 15 (divider height)\n        assertThat(view1.top - view3!!.top, isEqualAllowingError(activity.dpToPixel(160)))\n        view4 = layoutManager.getChildAt(3)\n        // 90 (view width)\n        assertThat(view4!!.left, isEqualAllowingError(activity.dpToPixel(90)))\n        view7 = layoutManager.getChildAt(6)\n        // 90 (view width) + 90 (view width)\n        assertThat(view7!!.left, isEqualAllowingError(activity.dpToPixel(180)))\n\n        activityRule.runOnUiThread {\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.removeItemDecoration(itemDecoration)\n            itemDecoration.setOrientation(VERTICAL)\n            recyclerView.addItemDecoration(itemDecoration)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        view1 = layoutManager.getChildAt(0)\n        view2 = layoutManager.getChildAt(1)\n        // 65 (view height)\n        assertThat(view1!!.top - view2!!.top, isEqualAllowingError(activity.dpToPixel(65)))\n        view3 = layoutManager.getChildAt(2)\n        // 65 (view height) + 65 (view height)\n        assertThat(view1.top - view3!!.top, isEqualAllowingError(activity.dpToPixel(130)))\n        view4 = layoutManager.getChildAt(3)\n        // 90 (view width) + 10 (divider width)\n        assertThat(view4!!.left, isEqualAllowingError(activity.dpToPixel(100)))\n        view7 = layoutManager.getChildAt(6)\n        // 90 (view width) + 10 (divider width) + 90 (view width) + 10 (divider width)\n        assertThat(view7!!.left, isEqualAllowingError(activity.dpToPixel(200)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToPosition_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..149) {\n                val lp = createLayoutParams(activity, 100, 70)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 3 items\n            // Flex line 2: 3 items\n            // ....\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n\n        val scrollTo = 42\n        activityRule.runOnUiThread { layoutManager.scrollToPosition(scrollTo) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // Each flex line should have 3 items in this test's configuration.\n        // After scrolling to the position of 42 (% 3 == 0), the first visible item should\n        // be the 42'th item\n        assertThat((layoutManager.getChildAt(0) as TextView).text.toString(),\n                `is`((scrollTo + 1).toString()))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        // Scroll enough that 42'th item becomes off screen to the top\n\n        activityRule.runOnUiThread { layoutManager.scrollToPosition(scrollTo) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // The 42'th item should be at the bottom of the screen.\n        // The last visible item should be 42 + 3 since the last visible item is at the last\n        // of the bottom flex line\n        assertThat((layoutManager.getChildAt(layoutManager.childCount - 1) as TextView).text.toString(),\n                `is`((scrollTo + 3).toString()))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToPosition_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..149) {\n                val lp = createLayoutParams(activity, 100, 70)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 3 items\n            // Flex line 2: 3 items\n            // ....\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n\n        val scrollTo = 42\n        activityRule.runOnUiThread { layoutManager.scrollToPosition(scrollTo) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // Each flex line should have 3 items in this test's configuration.\n        // After scrolling to the position of 42 (% 3 == 0), the first visible item should\n        // be the 42'th item\n        assertThat((layoutManager.getChildAt(0) as TextView).text.toString(),\n                `is`((scrollTo + 1).toString()))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        // Scroll enough that 42'th item becomes off screen to the left\n\n        activityRule.runOnUiThread { layoutManager.scrollToPosition(scrollTo) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // The 42'th item should be at the bottom of the screen.\n        // The last item should be the (42 + 3)'th item since it should be also the last item in the\n        // bottom flex line\n        assertThat((layoutManager.getChildAt(layoutManager.childCount - 1) as TextView).text.toString(),\n                `is`((scrollTo + 3).toString()))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToPosition_scrollToNewItem_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..5) {\n                val lp = createLayoutParams(activity, 100, 70)\n                adapter.addItem(lp)\n            }\n            // There should be 2 lines\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 3 items\n            // Flex line 2: 3 items\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n\n        activityRule.runOnUiThread {\n            val lp = createLayoutParams(activity, 100, 70)\n            adapter.addItem(lp)\n            layoutManager.scrollToPosition(adapter.itemCount - 1)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // ChildCount (visible views) should be 6 + 1,\n        // which before fixing https://github.com/google/flexbox-layout/issues/206, only the new\n        // item was visible\n        assertThat(layoutManager.childCount, `is`(7))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToPosition_scrollToNewItem_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..5) {\n                val lp = createLayoutParams(activity, 100, 70)\n                adapter.addItem(lp)\n            }\n            // There should be 2 lines\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 3 items\n            // Flex line 2: 3 items\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n\n        activityRule.runOnUiThread {\n            val lp = createLayoutParams(activity, 100, 70)\n            adapter.addItem(lp)\n            layoutManager.scrollToPosition(adapter.itemCount - 1)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // ChildCount (visible views) should be 6 + 1,\n        // which before fixing https://github.com/google/flexbox-layout/issues/206, only the new\n        // item was visible\n        assertThat(layoutManager.childCount, `is`(7))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollToStart_secondLineHasMoreItemThanFirst() {\n        // This test verifies the case that the first line disappears as the user first scrolls to\n        // the bottom enough that the first line becomes invisible then the user scrolls toward\n        // start on the condition that the second line has more items than the first line\n        // https://github.com/google/flexbox-layout/issues/228\n\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val first = FlexboxLayoutManager.LayoutParams(\n                    ViewGroup.LayoutParams.MATCH_PARENT, activity.dpToPixel(70))\n            adapter.addItem(first)\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 100, 70)\n                adapter.addItem(lp)\n            }\n            // The first line has 1 item, the following lines have more than 1 items\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 1 items\n            // Flex line 2: 3 items\n            // Flex line 3: 3 items\n            // ...\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        // At this moment, the first item should become invisible\n        var firstView = layoutManager.getChildAt(0)\n        assertThat((firstView as TextView).text.toString(), `is`(not(\"1\")))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n\n        // The first visible item should be \"1\", which before fixing the issue\n        // https://github.com/google/flexbox-layout/issues/228, the first line disappeared.\n        firstView = layoutManager.getChildAt(0)\n        assertThat((firstView as TextView).text.toString(), `is`(\"1\"))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testNestedRecyclerViews_direction_row() {\n        // This test verifies the nested RecyclerViews.\n        // The outer RecyclerView scrolls vertical using LinearLayoutManager.\n        // The inner RecyclerViews use FlexboxLayoutManager with flexDirection == ROW and\n        // height of the RecyclerView is set to \"wrap_content\", which before fixing\n        // https://github.com/google/flexbox-layout/issues/208, the height of the inner\n        // RecyclerViews were set to 0.\n        val activity = activityRule.activity\n        val outerLayoutManager = LinearLayoutManager(activity)\n\n        // Give the inner adapter item count enough so that inner RecyclerView with\n        // FlexboxLayoutManager wraps its items\n        val innerAdapterItemCount = 20\n        val adapter = NestedOuterAdapter(FlexDirection.ROW,\n                innerAdapterItemCount, R.layout.viewholder_inner_recyclerview)\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            outerLayoutManager.orientation = LinearLayoutManager.VERTICAL\n            recyclerView.layoutManager = outerLayoutManager\n            recyclerView.adapter = adapter\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val viewHolder = adapter.getViewHolder(0)\n        val innerRecyclerView = viewHolder.innerRecyclerView\n        assertThat(innerRecyclerView.height, `is`(not(0)))\n\n        // This assertion verifies that inner RecyclerView displays the entire items including\n        // wrapped lines to verify the issue that nested RecyclerView with FlexboxLayoutManager\n        // only displayed one line https://github.com/google/flexbox-layout/issues/290\n        assertThat((innerRecyclerView.layoutManager as FlexboxLayoutManager).findLastVisibleItemPosition(),\n                `is`(innerAdapterItemCount - 1))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testNestedRecyclerViews_direction_column() {\n        // This test verifies the nested RecyclerViews.\n        // The outer RecyclerView scrolls horizontally using LinearLayoutManager.\n        // The inner RecyclerViews use FlexboxLayoutManager with flexDirection == COLUMN and\n        // width of the RecyclerView is set to \"wrap_content\", which before fixing\n        // https://github.com/google/flexbox-layout/issues/208, the width of the inner\n        // RecyclerViews were set to 0.\n        val activity = activityRule.activity\n        val outerLayoutManager = LinearLayoutManager(activity)\n\n        // Give the inner adapter item count enough so that inner RecyclerView with\n        // FlexboxLayoutManager wraps its items\n        val innerAdapterItemCount = 20\n        val adapter = NestedOuterAdapter(FlexDirection.COLUMN,\n                innerAdapterItemCount, R.layout.viewholder_inner_recyclerview_wrap_horizontally)\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            outerLayoutManager.orientation = LinearLayoutManager.HORIZONTAL\n            recyclerView.layoutManager = outerLayoutManager\n            recyclerView.adapter = adapter\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val viewHolder = adapter.getViewHolder(0)\n        val innerRecyclerView = viewHolder.innerRecyclerView\n        assertThat(innerRecyclerView.width, `is`(not(0)))\n\n        // This assertion verifies that inner RecyclerView displays the entire items including\n        // wrapped lines to verify the issue that nested RecyclerView with FlexboxLayoutManager\n        // only displayed one line https://github.com/google/flexbox-layout/issues/290\n        assertThat((innerRecyclerView.layoutManager as FlexboxLayoutManager).findLastVisibleItemPosition(),\n                `is`(innerAdapterItemCount - 1))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFindVisibleChild_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 100, 75)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // At first three completely visible lines.\n            // Flex line 1, item count 3 (0, 1, 2)\n            // Flex line 2, item count 3 (3, 4, 5)\n            // Flex line 3, item count 3 (6, 7, 8)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.findFirstCompletelyVisibleItemPosition(), `is`(0))\n        assertThat(layoutManager.findFirstVisibleItemPosition(), `is`(0))\n        assertThat(layoutManager.findLastCompletelyVisibleItemPosition(), `is`(8))\n        assertThat(layoutManager.findLastVisibleItemPosition(), `is`(11))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.findFirstCompletelyVisibleItemPosition(), `is`(42))\n        assertThat(layoutManager.findFirstVisibleItemPosition(), `is`(39))\n        assertThat(layoutManager.findLastCompletelyVisibleItemPosition(), `is`(49))\n        assertThat(layoutManager.findLastVisibleItemPosition(), `is`(49))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testFindVisibleChild_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 100, 75)\n                adapter.addItem(lp)\n            }\n            // RecyclerView width: 320, height: 240.\n            // At first three completely visible lines.\n            // Flex line 1, item count 3 (0, 1, 2)\n            // Flex line 2, item count 3 (3, 4, 5)\n            // Flex line 3, item count 3 (6, 7, 8)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.findFirstCompletelyVisibleItemPosition(), `is`(0))\n        assertThat(layoutManager.findFirstVisibleItemPosition(), `is`(0))\n        assertThat(layoutManager.findLastCompletelyVisibleItemPosition(), `is`(8))\n        assertThat(layoutManager.findLastVisibleItemPosition(), `is`(11))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(layoutManager.findFirstCompletelyVisibleItemPosition(), `is`(42))\n        assertThat(layoutManager.findFirstVisibleItemPosition(), `is`(39))\n        assertThat(layoutManager.findLastCompletelyVisibleItemPosition(), `is`(49))\n        assertThat(layoutManager.findLastVisibleItemPosition(), `is`(49))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDrawDirtyFlexLine_direction_row() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..29) {\n                val lp = createLayoutParams(activity, 100, 75)\n                adapter.addItem(lp)\n            }\n        }\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // First scroll to the bottom, then add a new item that isn't visible at this moment.\n        activityRule.runOnUiThread {\n            val lp = createLayoutParams(activity, 40, 75)\n            adapter.addItem(0, lp)\n        }\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        val firstVisible = layoutManager.getChildAt(0)\n        assertThat(firstVisible!!.width, isEqualAllowingError(activity.dpToPixel(40)))\n        assertThat(firstVisible.height, isEqualAllowingError(activity.dpToPixel(75)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDrawDirtyFlexLine_direction_column() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n\n            for (i in 0..29) {\n                val lp = createLayoutParams(activity, 100, 75)\n                adapter.addItem(lp)\n            }\n        }\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // First scroll to the bottom, then add a new item that isn't visible at this moment.\n        activityRule.runOnUiThread {\n            val lp = createLayoutParams(activity, 100, 120)\n            adapter.addItem(0, lp)\n        }\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        val firstVisible = layoutManager.getChildAt(0)\n        assertThat(firstVisible!!.width, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(firstVisible.height, isEqualAllowingError(activity.dpToPixel(120)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testDrawDirtyFlexLine_multi_viewTypes_direction_row() {\n        // This test verifies https://github.com/google/flexbox-layout/issues/280\n        // the position of the view type is shifted if a new item is inserted before the\n        // view which has the special viewType and that view isn't visible at the time the item\n        // was inserted.\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapterMultiViewTypes()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val parent = activity.findViewById<RecyclerView>(R.id.recyclerview)\n        var matchParentText = layoutManager\n                .getChildAt(TestAdapterMultiViewTypes.POSITION_MATCH_PARENT) as TextView\n        assertThat(matchParentText.width, `is`(parent.width))\n        assertThat(matchParentText.text.toString(),\n                `is`<String>((TestAdapterMultiViewTypes.POSITION_MATCH_PARENT + 1).toString()))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n\n        val insertedValue = 10\n        activityRule.runOnUiThread {\n            val item = TestAdapterMultiViewTypes.Item()\n            item.value = insertedValue\n            // Insert an item before the position that has a special viewType\n            adapter.addItemAt(TestAdapterMultiViewTypes.POSITION_MATCH_PARENT - 1, item)\n        }\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        // Since a new item is inserted before the position, the index at the view who has the\n        // special viewType should be shifted.\n        matchParentText = layoutManager\n                .getChildAt(TestAdapterMultiViewTypes.POSITION_MATCH_PARENT + 1) as TextView\n        assertThat(matchParentText.width, `is`(parent.width))\n        assertThat(matchParentText.text.toString(),\n                `is`<String>((TestAdapterMultiViewTypes.POSITION_MATCH_PARENT + 1).toString()))\n\n        // The position of this view is the old position who had the special viewType, but\n        // now the viewType should be a normal one\n        val textView = layoutManager\n                .getChildAt(TestAdapterMultiViewTypes.POSITION_MATCH_PARENT - 1) as TextView\n        assertThat(textView.width, lessThan(parent.width))\n        assertThat(textView.text.toString(), `is`(insertedValue.toString()))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testChildrenSizeWithMargin() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp = createLayoutParams(activity, 100, 30)\n            lp.setMargins(10, 30, 20, 40)\n            adapter.addItem(lp)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val text = layoutManager.getChildAt(0) as TextView\n        val lp = text.layoutParams as FlexboxLayoutManager.LayoutParams\n        assertThat(text.height, isEqualAllowingError(activity.dpToPixel(30)))\n        assertThat(text.width, isEqualAllowingError(activity.dpToPixel(100)))\n        assertThat(lp.marginLeft, isEqualAllowingError(10))\n        assertThat(lp.marginRight, isEqualAllowingError(20))\n        assertThat(lp.marginTop, isEqualAllowingError(30))\n        assertThat(lp.marginBottom, isEqualAllowingError(40))\n        activityRule.runOnUiThread { layoutManager.flexDirection = FlexDirection.COLUMN }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val text2 = layoutManager.getChildAt(0) as TextView\n        assertThat(text2.height, isEqualAllowingError(activity.dpToPixel(30)))\n        assertThat(text2.width, isEqualAllowingError(activity.dpToPixel(100)))\n\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testItemDecoration_withScrolling_direction_row() {\n        // This test verifies the case that the item decoration set through FlexboxItemDecoration\n        // is misplaced after the user scrolls the RecyclerView\n        // https://github.com/google/flexbox-layout/issues/285\n\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val decorationDrawable = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val decoration = FlexboxItemDecoration(activity)\n            decoration.setDrawable(decorationDrawable)\n            recyclerView.addItemDecoration(decoration)\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 100, 70)\n                adapter.addItem(lp)\n            }\n            // The first line has 1 item, the following lines have more than 1 items\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 1 items\n            // Flex line 2: 3 items\n            // Flex line 3: 3 items\n            // ...\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.ROW))\n        assertThat(layoutManager.getTopDecorationHeight(layoutManager.getChildAt(0)!!), `is`(0))\n        assertThat(layoutManager.getTopDecorationHeight(layoutManager.getChildAt(1)!!), `is`(0))\n        assertThat(layoutManager.getTopDecorationHeight(layoutManager.getChildAt(2)!!), `is`(0))\n        layoutManager.flexLines\n                .mapNotNull { layoutManager.getChildAt(it.firstIndex) }\n                .forEach { assertThat(layoutManager.getLeftDecorationWidth(it), `is`(0)) }\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n\n        // Verify even after the scrolling, decoration values are set correctly\n        assertThat(layoutManager.getTopDecorationHeight(layoutManager.getChildAt(0)!!), `is`(0))\n        assertThat(layoutManager.getTopDecorationHeight(layoutManager.getChildAt(1)!!), `is`(0))\n        assertThat(layoutManager.getTopDecorationHeight(layoutManager.getChildAt(2)!!), `is`(0))\n        layoutManager.flexLines\n                .mapNotNull { layoutManager.getChildAt(it.firstIndex) }\n                .forEach { assertThat(layoutManager.getLeftDecorationWidth(it), `is`(0)) }\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testItemDecoration_withScrolling_direction_column() {\n        // This test verifies the case that the item decoration set through FlexboxItemDecoration\n        // is misplaced after the user scrolls the RecyclerView\n        // https://github.com/google/flexbox-layout/issues/285\n\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val decorationDrawable = ResourcesCompat.getDrawable(activity.resources, R.drawable.divider, null)\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val decoration = FlexboxItemDecoration(activity)\n            decoration.setDrawable(decorationDrawable)\n            recyclerView.addItemDecoration(decoration)\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 100, 70)\n                adapter.addItem(lp)\n            }\n            // The first line has 1 item, the following lines have more than 1 items\n            // RecyclerView width: 320, height: 240.\n            // Flex line 1: 1 items\n            // Flex line 2: 3 items\n            // Flex line 3: 3 items\n            // ...\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexDirection, `is`(FlexDirection.COLUMN))\n        assertThat(layoutManager.getLeftDecorationWidth(layoutManager.getChildAt(0)!!), `is`(0))\n        assertThat(layoutManager.getLeftDecorationWidth(layoutManager.getChildAt(1)!!), `is`(0))\n        assertThat(layoutManager.getLeftDecorationWidth(layoutManager.getChildAt(2)!!), `is`(0))\n        layoutManager.flexLines\n                .mapNotNull { layoutManager.getChildAt(it.firstIndex) }\n                .forEach { assertThat(layoutManager.getTopDecorationHeight(it), `is`(0)) }\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.recyclerview)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n\n        // Verify even after the scrolling, decoration values are set correctly\n        assertThat(layoutManager.getLeftDecorationWidth(layoutManager.getChildAt(0)!!), `is`(0))\n        assertThat(layoutManager.getLeftDecorationWidth(layoutManager.getChildAt(1)!!), `is`(0))\n        assertThat(layoutManager.getLeftDecorationWidth(layoutManager.getChildAt(2)!!), `is`(0))\n        layoutManager.flexLines\n                .mapNotNull { layoutManager.getChildAt(it.firstIndex) }\n                .forEach { assertThat(layoutManager.getTopDecorationHeight(it), `is`(0)) }\n    }\n\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testNotifyItemChange_withPayload() {\n        // This test verifies the payload is correctly passed to the Adapter in the case\n        // that notifying an item with payload\n        // https://github.com/google/flexbox-layout/issues/297\n\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            val lp = createLayoutParams(activity, 100, 70)\n            adapter.addItem(lp)\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(adapter.payloads.size, `is`(0))\n\n        val payload = \"payload\"\n        activityRule.runOnUiThread { adapter.changeItemWithPayload(0, payload) }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n\n        assertThat(adapter.payloads.size, `is`(1))\n        assertThat(adapter.payloads[0] as String, `is`(payload))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollAlongManAxis_direction_row() {\n        // This test verifies the scroll along the main axis if the width of the RecyclerView is\n        // larger than its parent when the main axis direction is horizontal (row)\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.wrapped_recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 100, 70)\n                adapter.addItem(lp)\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val view = layoutManager.getChildAt(0)!!\n        assertThat(view.left, `is`(0))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.CENTER_RIGHT,\n                GeneralLocation.CENTER_LEFT))\n        assertThat(view.left, `is`(not(0)))\n\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.CENTER_LEFT,\n                GeneralLocation.CENTER_RIGHT))\n        assertThat(view.left, `is`(0))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testScrollAlongManAxis_direction_column() {\n        // This test verifies the scroll along the main axis if the height of the RecyclerView is\n        // larger than its parent when the main axis direction is vertical (column).\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.wrapped_recyclerview_scroll_vertical)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 0..49) {\n                val lp = createLayoutParams(activity, 70, 100)\n                adapter.addItem(lp)\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val view = layoutManager.getChildAt(0)!!\n        assertThat(view.top, `is`(0))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.BOTTOM_CENTER,\n                GeneralLocation.TOP_CENTER))\n        assertThat(view.top, `is`(not(0)))\n\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        onView(withId(R.id.container)).perform(swipe(GeneralLocation.TOP_CENTER,\n                GeneralLocation.BOTTOM_CENTER))\n        assertThat(view.top, `is`(0))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testMaxLine() {\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.maxLine = 3\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 1..50) {\n                val lp = createLayoutParams(activity, 100, 70)\n                lp.flexShrink = 0f\n                adapter.addItem(lp)\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        assertThat(layoutManager.flexLines.size, `is`(3))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testNowrap_justifyContentCenter_directionRow() {\n        // This is to fix https://github.com/google/flexbox-layout/issues/469\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val height = 70\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.ROW\n            layoutManager.flexWrap = FlexWrap.NOWRAP\n            layoutManager.justifyContent = JustifyContent.CENTER\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 1..3) {\n                val lp = createLayoutParams(activity, 100, height)\n                adapter.addItem(lp)\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val view1Bottom= layoutManager.getChildAt(0)!!.bottom\n        val view2Bottom = layoutManager.getChildAt(1)!!.bottom\n        val view3Bottom = layoutManager.getChildAt(2)!!.bottom\n        assertThat(view1Bottom, `is`(activity.dpToPixel(height)))\n        assertThat(view2Bottom, `is`(activity.dpToPixel(height)))\n        assertThat(view3Bottom, `is`(activity.dpToPixel(height)))\n    }\n\n    @Test\n    @FlakyTest\n    @Throws(Throwable::class)\n    fun testNowrap_justifyContentCenter_directionColumn() {\n        // This is to fix https://github.com/google/flexbox-layout/issues/469\n        val activity = activityRule.activity\n        val layoutManager = FlexboxLayoutManager(activity)\n        val adapter = TestAdapter()\n        val width = 100\n        activityRule.runOnUiThread {\n            activity.setContentView(R.layout.recyclerview)\n            val recyclerView = activity.findViewById<RecyclerView>(R.id.recyclerview)\n            layoutManager.flexDirection = FlexDirection.COLUMN\n            layoutManager.flexWrap = FlexWrap.NOWRAP\n            layoutManager.justifyContent = JustifyContent.CENTER\n            recyclerView.layoutManager = layoutManager\n            recyclerView.adapter = adapter\n            for (i in 1..3) {\n                val lp = createLayoutParams(activity, width, 70)\n                adapter.addItem(lp)\n            }\n        }\n        InstrumentationRegistry.getInstrumentation().waitForIdleSync()\n        val view1Right= layoutManager.getChildAt(0)!!.right\n        val view2Right = layoutManager.getChildAt(1)!!.right\n        val view3Right = layoutManager.getChildAt(2)!!.right\n        assertThat(view1Right, `is`(activity.dpToPixel(width)))\n        assertThat(view2Right, `is`(activity.dpToPixel(width)))\n        assertThat(view3Right, `is`(activity.dpToPixel(width)))\n    }\n\n    /**\n     * Creates a new flex item.\n     *\n     * @param context the context\n     * @param width   in DP\n     * @param height  in DP\n     * @return the created [FlexboxLayoutManager.LayoutParams] instance\n     */\n    private fun createLayoutParams(context: Context, width: Int,\n                                   height: Int): FlexboxLayoutManager.LayoutParams {\n        return FlexboxLayoutManager.LayoutParams(context.dpToPixel(width), context.dpToPixel(height))\n    }\n\n    private fun swipe(from: CoordinatesProvider, to: CoordinatesProvider): ViewAction {\n        return GeneralSwipeAction(Swipe.FAST, from, to, Press.FINGER)\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/FlexboxTestActivity.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.app.Activity\nimport com.google.android.flexbox.FlexboxLayout\n\n/**\n * Activity for testing the [FlexboxLayout].\n */\nclass FlexboxTestActivity : Activity()\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/IsEqualAllowingError.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport org.hamcrest.BaseMatcher\nimport org.hamcrest.Description\nimport org.hamcrest.Factory\nimport org.hamcrest.Matcher\nimport java.util.*\n\n/**\n * Custom [BaseMatcher] that expects [Number] value allowing some errors to allow\n * such as rounding errors.\n */\nclass IsEqualAllowingError<T : Number> private constructor(private val expected: Number, private val errorAllowed: Int) : BaseMatcher<T>() {\n\n    override fun matches(item: Any): Boolean {\n        if (item !is Number) {\n            return false\n        }\n        return expected.toInt() - errorAllowed <= item.toInt() && item.toInt() <= expected.toInt() + errorAllowed\n    }\n\n    override fun describeTo(description: Description) {\n        description.appendText(\n                String.format(Locale.US, \"expected value is <%s> allowing error of <%s>.\", expected,\n                        errorAllowed))\n    }\n\n    companion object {\n\n        @Factory\n        fun <T : Number> isEqualAllowingError(expected: T): Matcher<T> {\n            return IsEqualAllowingError(expected, 2)\n        }\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/NestedInnerAdapter.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.view.LayoutInflater\nimport android.view.View\nimport android.view.ViewGroup\nimport android.widget.TextView\nimport androidx.recyclerview.widget.RecyclerView\n\n/**\n * Adapter for the tests for nested RecyclerViews.\n * This Adapter is used for the inner RecyclerView.\n */\ninternal class NestedInnerAdapter(private val innerPosition: Int, private val itemCount: Int)\n    : RecyclerView.Adapter<NestedInnerAdapter.InnerViewHolder>() {\n\n    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): NestedInnerAdapter.InnerViewHolder {\n        val view = LayoutInflater.from(parent.context).inflate(R.layout.viewholder_textview, parent, false)\n        return InnerViewHolder(view)\n    }\n\n    override fun onBindViewHolder(holder: InnerViewHolder, position: Int) {\n        holder.textView.text = holder.textView.resources.getString(R.string.item_description, innerPosition, position)\n    }\n\n    override fun getItemCount() = itemCount\n\n    internal class InnerViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {\n\n        val textView: TextView = itemView.findViewById(R.id.textview)\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/NestedOuterAdapter.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.view.LayoutInflater\nimport android.view.View\nimport android.view.ViewGroup\nimport androidx.annotation.LayoutRes\nimport androidx.recyclerview.widget.RecyclerView\nimport com.google.android.flexbox.FlexDirection\nimport com.google.android.flexbox.FlexboxLayoutManager\n\n/**\n * Adapter for the tests for nested RecyclerViews.\n * This Adapter is used for the outer RecyclerView.\n */\ninternal class NestedOuterAdapter(\n        @param:FlexDirection private val flexDirection: Int, private val innerAdapterItemCount: Int,\n        @param:LayoutRes private val viewHolderResId: Int\n) : RecyclerView.Adapter<NestedOuterAdapter.OuterViewHolder>() {\n\n    private val viewHolderList = mutableListOf<OuterViewHolder>()\n\n    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): OuterViewHolder {\n        val view = LayoutInflater.from(parent.context).inflate(viewHolderResId, parent, false)\n        val holder = OuterViewHolder(view)\n        viewHolderList.add(holder)\n        return holder\n    }\n\n    override fun onBindViewHolder(holder: OuterViewHolder, position: Int) {\n        val layoutManager = FlexboxLayoutManager(holder.itemView.context)\n        layoutManager.flexDirection = flexDirection\n        holder.innerRecyclerView.layoutManager = layoutManager\n        holder.innerRecyclerView.adapter = NestedInnerAdapter(position, innerAdapterItemCount)\n    }\n\n    fun getViewHolder(position: Int) = viewHolderList[position]\n\n    override fun getItemCount() = ITEM_COUNT\n\n    internal class OuterViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {\n        val innerRecyclerView: RecyclerView = itemView.findViewById(R.id.recyclerview_inner)\n    }\n\n    companion object {\n        private const val ITEM_COUNT = 4\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/TestAdapter.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.view.Gravity\nimport android.view.LayoutInflater\nimport android.view.ViewGroup\nimport androidx.recyclerview.widget.RecyclerView\nimport com.google.android.flexbox.FlexboxLayoutManager\n\n/**\n * [RecyclerView.Adapter] implementation for [TestViewHolder].\n */\ninternal class TestAdapter private constructor(\n        private val layoutParams: MutableList<FlexboxLayoutManager.LayoutParams>)\n    : RecyclerView.Adapter<TestViewHolder>() {\n\n    private val receivedPayloads = mutableListOf<Any>()\n\n    constructor() : this(mutableListOf<FlexboxLayoutManager.LayoutParams>())\n\n    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): TestViewHolder {\n        val view = LayoutInflater.from(parent.context)\n                .inflate(R.layout.recyclerview_viewholder, parent, false)\n        return TestViewHolder(view)\n    }\n\n    override fun onBindViewHolder(holder: TestViewHolder, position: Int) {\n        holder.textView.text = (position + 1).toString()\n        holder.textView.setBackgroundResource(R.drawable.flex_item_background)\n        holder.textView.gravity = Gravity.CENTER\n        holder.textView.layoutParams = layoutParams[position]\n    }\n\n    override fun onBindViewHolder(holder: TestViewHolder, position: Int, payloads: List<Any>) {\n        receivedPayloads.addAll(payloads)\n        onBindViewHolder(holder, position)\n    }\n\n    fun addItem(position: Int, flexItem: FlexboxLayoutManager.LayoutParams) {\n        layoutParams.add(position, flexItem)\n        notifyItemInserted(position)\n    }\n\n    fun addItem(flexItem: FlexboxLayoutManager.LayoutParams) {\n        layoutParams.add(flexItem)\n        notifyItemInserted(layoutParams.size - 1)\n    }\n\n    fun changeItemWithPayload(position: Int, payload: Any) {\n        notifyItemChanged(position, payload)\n    }\n\n    val payloads get() = receivedPayloads.toList()\n\n    fun getItemAt(index: Int) = layoutParams[index]\n\n    override fun getItemCount() = layoutParams.size\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/TestAdapterMultiViewTypes.kt",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.view.Gravity\nimport android.view.LayoutInflater\nimport android.view.ViewGroup\nimport androidx.recyclerview.widget.RecyclerView\nimport com.google.android.flexbox.FlexboxLayoutManager\n\n/**\n * [RecyclerView.Adapter] implementation for [TestViewHolder], which has multiple\n * view types.\n */\ninternal class TestAdapterMultiViewTypes : RecyclerView.Adapter<TestViewHolder>() {\n\n    private val items = mutableListOf<Item>()\n\n    init {\n        for (i in 0 until ITEMS) {\n            val item = Item()\n            if (i == POSITION_MATCH_PARENT) {\n                item.viewType = VIEW_TYPE_MATCH_PARENT\n            }\n            item.value = i + 1\n            items.add(item)\n        }\n    }\n\n    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): TestViewHolder {\n        val view = LayoutInflater.from(parent.context)\n                .inflate(R.layout.recyclerview_viewholder, parent, false)\n        if (viewType == VIEW_TYPE_MATCH_PARENT) {\n            val flexboxLp = view.layoutParams as FlexboxLayoutManager.LayoutParams\n            flexboxLp.flexBasisPercent = 90f\n            flexboxLp.flexGrow = 1f\n        }\n        return TestViewHolder(view)\n    }\n\n    override fun onBindViewHolder(holder: TestViewHolder, position: Int) {\n        holder.textView.text = items[position].value.toString()\n        holder.textView.setBackgroundResource(R.drawable.flex_item_background)\n        holder.textView.gravity = Gravity.CENTER\n    }\n\n    override fun getItemViewType(position: Int) = items[position].viewType\n\n    fun addItemAt(position: Int, item: Item) {\n        items.add(position, item)\n        notifyItemInserted(position)\n    }\n\n    override fun getItemCount() = items.size\n\n    internal class Item {\n        internal var viewType = VIEW_TYPE_NORMAL\n        internal var value = 0\n    }\n\n    companion object {\n\n        internal const val POSITION_MATCH_PARENT = 3\n        private const val ITEMS = 50\n\n        private const val VIEW_TYPE_NORMAL = 0\n        private const val VIEW_TYPE_MATCH_PARENT = 1\n    }\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/TestUtil.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.content.Context\n\ninternal fun Context.dpToPixel(dp: Int): Int {\n    val displayMetrics = this.resources.displayMetrics\n    return if (dp < 0) dp else Math.round(dp * displayMetrics.density)\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/java/com/google/android/flexbox/test/TestViewHolder.kt",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox.test\n\nimport android.view.View\nimport android.widget.TextView\nimport androidx.recyclerview.widget.RecyclerView\n\n/**\n * ViewHolder implementation for a flex item for testing.\n */\ninternal class TestViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {\n    val textView: TextView = itemView.findViewById(R.id.textview)\n}\n"
  },
  {
    "path": "flexbox/src/androidTest/res/drawable/divider.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<shape xmlns:android=\"http://schemas.android.com/apk/res/android\">\n    <size\n        android:width=\"10dp\"\n        android:height=\"15dp\" />\n    <solid android:color=\"#44A444\" />\n</shape>"
  },
  {
    "path": "flexbox/src/androidTest/res/drawable/divider_thick.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<shape xmlns:android=\"http://schemas.android.com/apk/res/android\">\n    <size\n        android:width=\"40dp\"\n        android:height=\"42dp\" />\n    <solid android:color=\"#44A444\" />\n</shape>"
  },
  {
    "path": "flexbox/src/androidTest/res/drawable/flex_item_background.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<shape xmlns:android=\"http://schemas.android.com/apk/res/android\" android:shape=\"rectangle\" >\n    <solid android:color=\"#11aabb\" />\n    <stroke android:width=\"1dp\" android:color=\"#888888\"/>\n</shape>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_align_content_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignContent=\"stretch\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_align_content_test_overflowed.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2017 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap_reverse\"\n    app:alignContent=\"stretch\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"3\" />\n\n    <TextView\n        android:id=\"@+id/text4\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"4\" />\n\n    <TextView\n        android:id=\"@+id/text5\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"5\" />\n\n    <TextView\n        android:id=\"@+id/text6\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"6\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_align_items_baseline_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"baseline\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"30dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\"\n        android:gravity=\"bottom\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"30dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"2\"\n        android:gravity=\"top\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"30dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\"\n        android:paddingTop=\"20dp\"\n        android:gravity=\"center\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_align_items_baseline_wrap_content.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2017 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"baseline\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"30dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\"\n        android:gravity=\"bottom\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"30dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"2\"\n        android:gravity=\"top\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"30dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\"\n        android:paddingTop=\"20dp\"\n        android:gravity=\"center\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_align_items_parent_padding_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    android:padding=\"16dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_end\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_align_items_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignContent=\"stretch\"\n    app:alignItems=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_align_self_stretch_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_start\"\n    app:alignContent=\"stretch\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"1\"\n        app:layout_alignSelf=\"stretch\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_child_needs_remeasure_column.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2017 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"wrap\"\n    app:alignContent=\"stretch\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\"\n        app:layout_flexGrow=\"1.0\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"2\"\n        app:layout_wrapBefore=\"true\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_child_needs_remeasure_row.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2017 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignContent=\"stretch\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"100dp\"\n        android:text=\"1\"\n        app:layout_flexGrow=\"1.0\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"match_parent\"\n        android:text=\"2\"\n        app:layout_wrapBefore=\"true\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"match_parent\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_direction_column_align_items_center_margin_oneside.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"100dp\"\n    android:layout_height=\"20dp\"\n    app:flexDirection=\"column\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"20dp\"\n        android:layout_height=\"match_parent\"\n        android:layout_marginRight=\"20dp\"\n        android:text=\"1\"\n        app:layout_alignSelf=\"center\" />\n\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_direction_row_align_items_center_margin_oneside.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"20dp\"\n    android:layout_height=\"100dp\"\n    app:flexDirection=\"row\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"20dp\"\n        android:layout_marginBottom=\"20dp\"\n        android:text=\"1\"\n        app:layout_alignSelf=\"center\" />\n\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_divider_test_direction_column.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"wrap\"\n    app:alignContent=\"flex_start\"\n    app:alignItems=\"flex_start\"\n    app:dividerDrawableHorizontal=\"@drawable/divider\"\n    app:showDividerHorizontal=\"beginning\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"90dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"90dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"90dp\"\n        android:text=\"3\" />\n\n    <TextView\n        android:id=\"@+id/text4\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"140dp\"\n        android:text=\"4\" />\n\n    <TextView\n        android:id=\"@+id/text5\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"140dp\"\n        android:text=\"5\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_divider_test_direction_row.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignContent=\"flex_start\"\n    app:alignItems=\"flex_start\"\n    app:dividerDrawableVertical=\"@drawable/divider\"\n    app:showDividerVertical=\"beginning\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"90dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"90dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"90dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\" />\n\n    <TextView\n        android:id=\"@+id/text4\"\n        android:layout_width=\"140dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"4\" />\n\n    <TextView\n        android:id=\"@+id/text5\"\n        android:layout_width=\"140dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"5\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_empty_children.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexWrap=\"wrap\">\n\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_first_item_large_horizontal_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"stretch\"\n    app:alignContent=\"stretch\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"500dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"300dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_first_item_large_vertical_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"stretch\"\n    app:alignContent=\"stretch\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"500dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"6dp\"\n        android:layout_height=\"300dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_first_view_gone_first_line_single_item.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2017 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<!--\nThis layout verifies the case where the first view's visibility is gone and the second view is\nin the next flex line by setting the layout_wrapBefore=\"true\"\n-->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"stretch\"\n    app:alignContent=\"stretch\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"1\"\n        android:visibility=\"gone\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"2\"\n        app:layout_wrapBefore=\"true\"\n    />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"3\"\n        app:layout_wrapBefore=\"true\"\n    />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_first_view_gone_layout_grow_set_for_rest.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2017 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<!--\nThis layout verifies the case where the first view's visibility is gone and the second view is\nin the next flex line by setting the layout_wrapBefore=\"true\"\n-->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"stretch\"\n    app:alignContent=\"stretch\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"1\"\n        android:visibility=\"gone\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"2\"\n        app:layout_wrapBefore=\"true\"\n        app:layout_flexGrow=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"3\"\n        app:layout_flexGrow=\"1\"\n        app:layout_wrapBefore=\"true\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_first_view_gone_layout_shrink_set_for_rest.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2017 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<!--\nThis layout verifies the case where the first view's visibility is gone and the second view is\nin the next flex line by setting the layout_wrapBefore=\"true\"\n-->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"320dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"stretch\"\n    app:alignContent=\"stretch\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"1\"\n        android:visibility=\"gone\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"120dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"2\"\n        app:layout_wrapBefore=\"true\"\n        app:layout_flexShrink=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"3\"\n        app:layout_flexShrink=\"1\"\n        app:layout_wrapBefore=\"true\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_flex_basis_percent_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"0dp\"\n        android:layout_height=\"0dp\"\n        app:layout_flexBasisPercent=\"50%\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"0dp\"\n        android:layout_height=\"0dp\"\n        app:layout_flexBasisPercent=\"60%\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_flex_grow_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"3\"\n        app:layout_flexGrow=\"1\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_flex_item_match_parent.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_start\"\n    app:alignContent=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"80dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_flex_item_match_parent_direction_column.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_start\"\n    app:alignContent=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"40dp\"\n        android:layout_height=\"match_parent\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"40dp\"\n        android:layout_height=\"match_parent\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"40dp\"\n        android:layout_height=\"match_parent\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_flex_wrap_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"360dp\"\n    android:layout_height=\"300dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_start\"\n    app:alignContent=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"1\"\n        app:layout_flexShrink=\"0\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\"\n        app:layout_flexShrink=\"0\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"3\"\n        app:layout_flexShrink=\"0\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_flexbox_wrap_content.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  --><!-- Set the layout_width and layout_height as wrap_content to test the behavior of\n     the situation MeasureSpec.AT_MOST is set as width/height mode -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"wrap_content\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_flexbox_wrapped_with_horizontalscrollview.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<!-- Wrap the FlexboxLayout with a Scrollview to test\n     the situation MeasureSpec.UNSPECIFIED is set as height mode -->\n<HorizontalScrollView xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\">\n\n    <com.google.android.flexbox.FlexboxLayout xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n        android:id=\"@+id/flexbox_layout\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"400dp\"\n        app:flexDirection=\"column\"\n        app:flexWrap=\"wrap\">\n\n        <TextView\n            android:id=\"@+id/text1\"\n            android:layout_width=\"300dp\"\n            android:layout_height=\"match_parent\"\n            android:text=\"1\" />\n\n        <TextView\n            android:id=\"@+id/text2\"\n            android:layout_width=\"300dp\"\n            android:layout_height=\"match_parent\"\n            android:text=\"2\" />\n\n        <TextView\n            android:id=\"@+id/text3\"\n            android:layout_width=\"300dp\"\n            android:layout_height=\"match_parent\"\n            android:text=\"3\" />\n    </com.google.android.flexbox.FlexboxLayout>\n</HorizontalScrollView>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_flexbox_wrapped_with_scrollview.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<!-- Wrap the FlexboxLayout with a Scrollview to test\n     the situation MeasureSpec.UNSPECIFIED is set as height mode -->\n<ScrollView xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\">\n\n    <com.google.android.flexbox.FlexboxLayout xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n        android:id=\"@+id/flexbox_layout\"\n        android:layout_width=\"360dp\"\n        android:layout_height=\"wrap_content\"\n        app:flexDirection=\"row\"\n        app:flexWrap=\"wrap\">\n\n        <TextView\n            android:id=\"@+id/text1\"\n            android:layout_width=\"140dp\"\n            android:layout_height=\"500dp\"\n            android:text=\"1\" />\n\n        <TextView\n            android:id=\"@+id/text2\"\n            android:layout_width=\"140dp\"\n            android:layout_height=\"500dp\"\n            android:text=\"2\" />\n\n        <TextView\n            android:id=\"@+id/text3\"\n            android:layout_width=\"140dp\"\n            android:layout_height=\"500dp\"\n            android:text=\"3\" />\n    </com.google.android.flexbox.FlexboxLayout>\n</ScrollView>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_justify_content_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"row\"\n    app:justifyContent=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_justify_content_with_gone.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"row\"\n    app:justifyContent=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"2\"\n        android:visibility=\"gone\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"60dp\"\n        android:layout_height=\"60dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_justify_content_with_parent_padding.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<FrameLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/frame_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    android:padding=\"24dp\">\n\n    <com.google.android.flexbox.FlexboxLayout\n        android:id=\"@+id/flexbox_layout\"\n        android:layout_width=\"match_parent\"\n        android:layout_height=\"match_parent\"\n        android:padding=\"8dp\"\n        app:flexDirection=\"row\"\n        app:justifyContent=\"flex_start\">\n\n        <TextView\n            android:id=\"@+id/text1\"\n            android:layout_width=\"60dp\"\n            android:layout_height=\"60dp\"\n            android:text=\"1\" />\n\n        <TextView\n            android:id=\"@+id/text2\"\n            android:layout_width=\"60dp\"\n            android:layout_height=\"60dp\"\n            android:text=\"2\" />\n\n        <TextView\n            android:id=\"@+id/text3\"\n            android:layout_width=\"60dp\"\n            android:layout_height=\"60dp\"\n            android:text=\"3\" />\n    </com.google.android.flexbox.FlexboxLayout>\n</FrameLayout>\n\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_maxheight_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout android:id=\"@+id/flexbox_layout\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\"\n    app:flexDirection=\"column\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"150dp\"\n        android:text=\"1\"\n        app:layout_maxHeight=\"100dp\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"0dp\"\n        android:text=\"2\"\n        app:layout_flexGrow=\"1\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_maxheight_upper_bound_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout android:id=\"@+id/flexbox_layout\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"nowrap\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"100dp\"\n        android:text=\"1\"\n        app:layout_flexGrow=\"1\"\n        app:layout_maxHeight=\"150dp\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"100dp\"\n        app:layout_flexGrow=\"1\"\n        android:text=\"2\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_maxwidth_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout android:id=\"@+id/flexbox_layout\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"150dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\"\n        app:layout_maxWidth=\"100dp\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"0dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"2\"\n        app:layout_flexGrow=\"1\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_maxwidth_upper_bound_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout android:id=\"@+id/flexbox_layout\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\"\n    app:flexWrap=\"nowrap\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\"\n        app:layout_flexGrow=\"1\"\n        app:layout_maxWidth=\"150dp\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"wrap_content\"\n        app:layout_flexGrow=\"1\"\n        android:text=\"2\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_minheight_lower_bound_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout android:id=\"@+id/flexbox_layout\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"nowrap\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"200dp\"\n        android:text=\"1\"\n        app:layout_minHeight=\"150dp\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"200dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"200dp\"\n        android:text=\"3\" />\n\n    <TextView\n        android:id=\"@+id/text4\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"200dp\"\n        android:text=\"4\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_minheight_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout android:id=\"@+id/flexbox_layout\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\"\n    app:flexDirection=\"column\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\"\n        app:layout_minHeight=\"100dp\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"0dp\"\n        android:text=\"2\"\n        app:layout_flexGrow=\"1\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_minwidth_lower_bound_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout android:id=\"@+id/flexbox_layout\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\"\n    app:flexWrap=\"nowrap\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"200dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\"\n        app:layout_minWidth=\"150dp\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"200dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"200dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"3\" />\n\n    <TextView\n        android:id=\"@+id/text4\"\n        android:layout_width=\"200dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"4\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_minwidth_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout android:id=\"@+id/flexbox_layout\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"400dp\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\"\n        app:layout_minWidth=\"100dp\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"0dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"2\"\n        app:layout_flexGrow=\"1\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_order_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\">\n\n    <TextView\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\"\n        app:layout_order=\"2\" />\n\n    <TextView\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"2\"\n        app:layout_order=\"-1\" />\n\n    <TextView\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"3\"\n        app:layout_order=\"0\" />\n\n    <TextView\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"4\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_simple.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"row_reverse\"\n    app:justifyContent=\"center\"\n    app:alignContent=\"center\"\n    app:alignItems=\"center\">\n\n    <TextView\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"wrap_content\"\n        app:layout_order=\"2\"\n        app:layout_flexGrow=\"1\"\n        app:layout_alignSelf=\"stretch\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_stretch_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"360dp\"\n    android:layout_height=\"360dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"stretch\"\n    app:alignContent=\"stretch\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"140dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"140dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"140dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_views_visibility_gone.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"360dp\"\n    android:layout_height=\"300dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"1\"\n        android:visibility=\"gone\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\"\n        android:visibility=\"gone\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"3\" />\n\n    <TextView\n        android:id=\"@+id/text4\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"4\" />\n\n    <TextView\n        android:id=\"@+id/text5\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"5\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_views_visibility_invisible.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"360dp\"\n    android:layout_height=\"300dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"1\"\n        android:visibility=\"invisible\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"2\"\n        android:visibility=\"invisible\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"120dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_visibility_gone_first_item_in_flex_line_column.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"360dp\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"wrap\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"160dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"160dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"160dp\"\n        android:visibility=\"gone\"\n        android:text=\"3\" />\n\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_visibility_gone_first_item_in_flex_line_row.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"360dp\"\n    android:layout_height=\"wrap_content\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"160dp\"\n        android:layout_height=\"wrap_content\"\n        android:visibility=\"gone\"\n        android:text=\"3\" />\n\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_before_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"360dp\"\n    android:layout_height=\"wrap_content\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"2\"\n        app:layout_wrapBefore=\"true\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\"\n        app:layout_wrapBefore=\"true\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_child_margin_horizontal_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"360dp\"\n    android:layout_height=\"wrap_content\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"280dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"30dp\"\n        android:layout_height=\"80dp\"\n        android:layout_margin=\"32dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_child_margin_vertical_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"360dp\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"280dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"30dp\"\n        android:layout_margin=\"32dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_content_child_bottom_margin_column_grow.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"wrap\"\n    app:justifyContent=\"flex_end\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"24dp\"\n        android:layout_height=\"0dp\"\n        android:layout_marginEnd=\"12dp\"\n        android:layout_marginRight=\"12dp\"\n        android:text=\"1\"\n        app:layout_flexBasisPercent=\"50%\"\n        app:layout_flexGrow=\"1\"\n        app:layout_flexShrink=\"0\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_content_child_bottom_margin_column_shrink.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"200dp\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"nowrap\"\n    app:justifyContent=\"flex_end\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"24dp\"\n        android:layout_height=\"150dp\"\n        android:layout_marginEnd=\"12dp\"\n        android:layout_marginRight=\"12dp\"\n        android:text=\"1\"\n        app:layout_flexShrink=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"12dp\"\n        android:layout_height=\"100dp\"\n        android:text=\"2\"\n        app:layout_flexShrink=\"1\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_content_child_bottom_margin_row_grow.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\"\n    app:flexWrap=\"wrap\"\n    app:justifyContent=\"flex_end\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"0dp\"\n        android:layout_height=\"24dp\"\n        android:layout_marginBottom=\"12dp\"\n        android:text=\"test\"\n        app:layout_flexBasisPercent=\"50%\"\n        app:layout_flexGrow=\"1\"\n        app:layout_flexShrink=\"0\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_content_child_bottom_margin_row_shrink.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"200dp\"\n    android:layout_height=\"wrap_content\"\n    app:flexWrap=\"nowrap\"\n    app:justifyContent=\"flex_end\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"150dp\"\n        android:layout_height=\"24dp\"\n        android:layout_marginBottom=\"12dp\"\n        android:text=\"test1\"\n        app:layout_flexShrink=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"12dp\"\n        android:text=\"test2\"\n        app:layout_flexShrink=\"1\" />\n</com.google.android.flexbox.FlexboxLayout>\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_parent_padding_horizontal_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"360dp\"\n    android:layout_height=\"wrap_content\"\n    android:padding=\"32dp\"\n    app:flexDirection=\"row\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"280dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"30dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"100dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_wrap_parent_padding_vertical_test.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  Copyright 2016 Google Inc. All rights reserved.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"360dp\"\n    android:padding=\"32dp\"\n    app:flexDirection=\"column\"\n    app:flexWrap=\"wrap\"\n    app:alignItems=\"flex_start\">\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"280dp\"\n        android:text=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"30dp\"\n        android:text=\"2\" />\n\n    <TextView\n        android:id=\"@+id/text3\"\n        android:layout_width=\"80dp\"\n        android:layout_height=\"80dp\"\n        android:text=\"3\" />\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_zero_height_positive_flexgrow.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"match_parent\"\n    app:flexDirection=\"column\"\n    app:alignItems=\"flex_start\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"0dp\"\n        android:text=\"1\"\n        app:layout_flexGrow=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"wrap_content\"\n        android:layout_height=\"0dp\"\n        android:text=\"2-some long text\"\n        app:layout_flexGrow=\"1\" />\n\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/activity_zero_width_positive_flexgrow.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<com.google.android.flexbox.FlexboxLayout xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:id=\"@+id/flexbox_layout\"\n    android:layout_width=\"match_parent\"\n    android:layout_height=\"wrap_content\"\n    app:alignItems=\"flex_start\" >\n\n    <TextView\n        android:id=\"@+id/text1\"\n        android:layout_width=\"0dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"1\"\n        app:layout_flexGrow=\"1\" />\n\n    <TextView\n        android:id=\"@+id/text2\"\n        android:layout_width=\"0dp\"\n        android:layout_height=\"wrap_content\"\n        android:text=\"2-some long text\"\n        app:layout_flexGrow=\"1\" />\n\n</com.google.android.flexbox.FlexboxLayout>"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/recyclerview.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<!-- Some APIs in espresso requires the view being performed is at least 90% visible to the\n     user, using the small width so that low resolution devices are covered-->\n<androidx.recyclerview.widget.RecyclerView android:id=\"@+id/recyclerview\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:layout_width=\"320dp\"\n    android:layout_height=\"240dp\" />\n\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/recyclerview_reverse.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n\n<androidx.recyclerview.widget.RecyclerView android:id=\"@+id/recyclerview\"\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    xmlns:app=\"http://schemas.android.com/apk/res-auto\"\n    android:layout_width=\"400dp\"\n    android:layout_height=\"match_parent\"\n    android:orientation=\"horizontal\"\n    app:reverseLayout=\"true\"\n    app:stackFromEnd=\"true\"\n    app:layoutManager=\"com.google.android.flexbox.FlexboxLayoutManager\" />\n\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/recyclerview_viewholder.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2016 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n\n<TextView xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/textview\"\n    android:layout_width=\"120dp\"\n    android:layout_height=\"80dp\" />\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/viewholder_inner_recyclerview.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2017 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<!-- The nested RecyclerViews tests verify the wrap_content behavior -->\n<androidx.recyclerview.widget.RecyclerView\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/recyclerview_inner\"\n    android:layout_width=\"200dp\"\n    android:layout_height=\"wrap_content\"\n    android:layout_marginBottom=\"8dp\" />\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/viewholder_inner_recyclerview_wrap_horizontally.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2017 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<!-- The nested RecyclerViews tests verify the wrap_content behavior -->\n<androidx.recyclerview.widget.RecyclerView\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/recyclerview_inner\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"200dp\"\n    android:layout_marginBottom=\"8dp\" />\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/viewholder_textview.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2017 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<TextView\n    xmlns:android=\"http://schemas.android.com/apk/res/android\"\n    android:id=\"@+id/textview\"\n    android:layout_width=\"wrap_content\"\n    android:layout_height=\"wrap_content\"\n    android:layout_margin=\"4dp\" />\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/wrapped_recyclerview.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2017 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<!-- Some APIs in espresso requires the view being performed is at least 90% visible to the\n     user, using the small width so that low resolution devices are covered-->\n<FrameLayout android:id=\"@+id/container\"\n             xmlns:android=\"http://schemas.android.com/apk/res/android\"\n             android:layout_width=\"320dp\"\n             android:layout_height=\"240dp\">\n    <androidx.recyclerview.widget.RecyclerView android:id=\"@+id/recyclerview\"\n                                            android:layout_width=\"600dp\"\n                                            android:layout_height=\"match_parent\"/>\n</FrameLayout>\n\n"
  },
  {
    "path": "flexbox/src/androidTest/res/layout/wrapped_recyclerview_scroll_vertical.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\n  ~ Copyright 2017 Google Inc. All rights reserved.\n  ~\n  ~ Licensed under the Apache License, Version 2.0 (the \"License\");\n  ~ you may not use this file except in compliance with the License.\n  ~ You may obtain a copy of the License at\n  ~\n  ~      http://www.apache.org/licenses/LICENSE-2.0\n  ~\n  ~ Unless required by applicable law or agreed to in writing, software\n  ~ distributed under the License is distributed on an \"AS IS\" BASIS,\n  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  ~ See the License for the specific language governing permissions and\n  ~ limitations under the License.\n  -->\n<!-- Some APIs in espresso requires the view being performed is at least 90% visible to the\n     user, using the small width so that low resolution devices are covered-->\n<FrameLayout android:id=\"@+id/container\"\n             xmlns:android=\"http://schemas.android.com/apk/res/android\"\n             android:layout_width=\"320dp\"\n             android:layout_height=\"240dp\">\n    <androidx.recyclerview.widget.RecyclerView android:id=\"@+id/recyclerview\"\n                                            android:layout_width=\"match_parent\"\n                                            android:layout_height=\"600dp\"/>\n</FrameLayout>\n\n"
  },
  {
    "path": "flexbox/src/androidTest/res/values/strings.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2017 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <string name=\"item_description\">%1$s - %2$s</string>\n</resources>\n"
  },
  {
    "path": "flexbox/src/main/AndroidManifest.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<manifest package=\"com.google.android.flexbox\" />\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/AlignContent.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport java.lang.annotation.Retention;\nimport java.lang.annotation.RetentionPolicy;\n\nimport androidx.annotation.IntDef;\n\n/** This attribute controls the alignment of the flex lines in the flex container. */\n@IntDef({AlignContent.FLEX_START, AlignContent.FLEX_END, AlignContent.CENTER,\n        AlignContent.SPACE_BETWEEN, AlignContent.SPACE_AROUND, AlignContent.STRETCH})\n@Retention(RetentionPolicy.SOURCE)\npublic @interface AlignContent {\n\n    /** Flex lines are packed to the start of the flex container. */\n    int FLEX_START = 0;\n\n    /** Flex lines are packed to the end of the flex container. */\n    int FLEX_END = 1;\n\n    /** Flex lines are centered in the flex container. */\n    int CENTER = 2;\n\n    /**\n     * Flex lines are evenly distributed in the flex container. The first flex line is\n     * placed at the start of the flex container, the last flex line is placed at the\n     * end of the flex container.\n     */\n    int SPACE_BETWEEN = 3;\n\n    /**\n     * Flex lines are evenly distributed in the flex container with the same amount of spaces\n     * between the flex lines.\n     */\n    int SPACE_AROUND = 4;\n\n    /**\n     * Flex lines are stretched to fill the remaining space along the cross axis.\n     */\n    int STRETCH = 5;\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/AlignItems.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport java.lang.annotation.Retention;\nimport java.lang.annotation.RetentionPolicy;\n\nimport androidx.annotation.IntDef;\n\n/** This attribute controls the alignment along the cross axis. */\n@IntDef({AlignItems.FLEX_START, AlignItems.FLEX_END, AlignItems.CENTER,\n        AlignItems.BASELINE, AlignItems.STRETCH})\n@Retention(RetentionPolicy.SOURCE)\npublic @interface AlignItems {\n\n    /** Flex item's edge is placed on the cross start line. */\n    int FLEX_START = 0;\n\n    /** Flex item's edge is placed on the cross end line. */\n    int FLEX_END = 1;\n\n    /** Flex item's edge is centered along the cross axis. */\n    int CENTER = 2;\n\n    /** Flex items are aligned based on their text's baselines. */\n    int BASELINE = 3;\n\n    /** Flex items are stretched to fill the flex line's cross size. */\n    int STRETCH = 4;\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/AlignSelf.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport java.lang.annotation.Retention;\nimport java.lang.annotation.RetentionPolicy;\n\nimport androidx.annotation.IntDef;\n\n/**\n * This attribute controls the alignment along the cross axis.\n * The alignment in the same direction can be determined by the {@link AlignItems} attribute in the\n * parent, but if this is set to other than {@link AlignSelf#AUTO},\n * the cross axis alignment is overridden for this child.\n */\n@IntDef({AlignItems.FLEX_START, AlignItems.FLEX_END, AlignItems.CENTER,\n        AlignItems.BASELINE, AlignItems.STRETCH, AlignSelf.AUTO})\n@Retention(RetentionPolicy.SOURCE)\npublic @interface AlignSelf {\n\n    /**\n     * The default value for the AlignSelf attribute, which means use the inherit\n     * the {@link AlignItems} attribute from its parent.\n     */\n    int AUTO = -1;\n\n    /** This item's edge is placed on the cross start line. */\n    int FLEX_START = AlignItems.FLEX_START;\n\n    /** This item's edge is placed on the cross end line. */\n    int FLEX_END = AlignItems.FLEX_END;\n\n    /** This item's edge is centered along the cross axis. */\n    int CENTER = AlignItems.CENTER;\n\n    /** This items is aligned based on their text's baselines. */\n    int BASELINE = AlignItems.BASELINE;\n\n    /** This item is stretched to fill the flex line's cross size. */\n    int STRETCH = AlignItems.STRETCH;\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexContainer.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport android.view.View;\n\nimport java.util.List;\n\n/**\n * An interface that has the common behavior as the flex container such as {@link FlexboxLayout}\n * and {@link FlexboxLayoutManager}.\n */\ninterface FlexContainer {\n\n    int NOT_SET = -1;\n\n    /**\n     * @return the number of flex items contained in the flex container.\n     */\n    int getFlexItemCount();\n\n    /**\n     * Returns a flex item as a View at the given index.\n     *\n     * @param index the index\n     * @return the view at the index\n     */\n    View getFlexItemAt(int index);\n\n    /**\n     * Returns a flex item as a View, which is reordered by taking the order attribute into\n     * account.\n     *\n     * @param index the index of the view\n     * @return the reordered view, which order attribute is taken into account.\n     * If the index is negative or out of bounds of the number of contained views,\n     * returns {@code null}.\n     * @see FlexItem#getOrder()\n     */\n    View getReorderedFlexItemAt(int index);\n\n    /**\n     * Adds the view to the flex container as a flex item.\n     *\n     * @param view the view to be added\n     */\n    void addView(View view);\n\n    /**\n     * Adds the view to the specified index of the flex container.\n     *\n     * @param view  the view to be added\n     * @param index the index for the view to be added\n     */\n    void addView(View view, int index);\n\n    /**\n     * Removes all the views contained in the flex container.\n     */\n    void removeAllViews();\n\n    /**\n     * Removes the view at the specified index.\n     *\n     * @param index the index from which the view is removed.\n     */\n    void removeViewAt(int index);\n\n    /**\n     * @return the flex direction attribute of the flex container.\n     * @see FlexDirection\n     */\n    @FlexDirection\n    int getFlexDirection();\n\n    /**\n     * Sets the given flex direction attribute to the flex container.\n     *\n     * @param flexDirection the flex direction value\n     * @see FlexDirection\n     */\n    void setFlexDirection(@FlexDirection int flexDirection);\n\n    /**\n     * @return the flex wrap attribute of the flex container.\n     * @see FlexWrap\n     */\n    @FlexWrap\n    int getFlexWrap();\n\n    /**\n     * Sets the given flex wrap attribute to the flex container.\n     *\n     * @param flexWrap the flex wrap value\n     * @see FlexWrap\n     */\n    void setFlexWrap(@FlexWrap int flexWrap);\n\n    /**\n     * @return the justify content attribute of the flex container.\n     * @see JustifyContent\n     */\n    @JustifyContent\n    int getJustifyContent();\n\n    /**\n     * Sets the given justify content attribute to the flex container.\n     *\n     * @param justifyContent the justify content value\n     * @see JustifyContent\n     */\n    void setJustifyContent(@JustifyContent int justifyContent);\n\n    /**\n     * @return the align content attribute of the flex container.\n     * @see AlignContent\n     */\n    @AlignContent\n    int getAlignContent();\n\n    /**\n     * Sets the given align content attribute to the flex container.\n     *\n     * @param alignContent the align content value\n     */\n    void setAlignContent(@AlignContent int alignContent);\n\n    /**\n     * @return the align items attribute of the flex container.\n     * @see AlignItems\n     */\n    @AlignItems\n    int getAlignItems();\n\n    /**\n     * Sets the given align items attribute to the flex container.\n     *\n     * @param alignItems the align items value\n     * @see AlignItems\n     */\n    void setAlignItems(@AlignItems int alignItems);\n\n    /**\n     * @return the flex lines composing this flex container. The overridden method should return a\n     * copy of the original list excluding a dummy flex line (flex line that doesn't have any flex\n     * items in it but used for the alignment along the cross axis) so that any changes of the\n     * returned list are not reflected to the original list.\n     */\n    List<FlexLine> getFlexLines();\n\n    /**\n     * Returns true if the main axis is horizontal, false otherwise.\n     *\n     * @return true if the main axis is horizontal, false otherwise\n     */\n    boolean isMainAxisDirectionHorizontal();\n\n    /**\n     * Returns the length of decoration (such as dividers) of the flex item along the main axis.\n     *\n     * @param view            the view from which the length of the decoration is retrieved\n     * @param index           the absolute index of the flex item within the flex container\n     * @param indexInFlexLine the relative index of the flex item within the flex line\n     * @return the length of the decoration. Note that the length of the flex item itself is not\n     * included in the result.\n     */\n    int getDecorationLengthMainAxis(View view, int index, int indexInFlexLine);\n\n    /**\n     * Returns the length of decoration (such as dividers) of the flex item along the cross axis.\n     *\n     * @param view the view from which the length of the decoration is retrieved\n     * @return the length of the decoration. Note that the length of the flex item itself is not\n     * included in the result.\n     */\n    int getDecorationLengthCrossAxis(View view);\n\n    /**\n     * @return the top padding of the flex container.\n     */\n    int getPaddingTop();\n\n    /**\n     * @return the left padding of the flex container.\n     */\n    int getPaddingLeft();\n\n    /**\n     * @return the right padding of the flex container.\n     */\n    int getPaddingRight();\n\n    /**\n     * @return the bottom padding of the flex container.\n     */\n    int getPaddingBottom();\n\n    /**\n     * @return the start padding of this view depending on its resolved layout direction.\n     */\n    int getPaddingStart();\n\n    /**\n     * @return the end padding of this view depending on its resolved layout direction.\n     */\n    int getPaddingEnd();\n\n    /**\n     * Returns the child measure spec for its width.\n     *\n     * @param widthSpec      the measure spec for the width imposed by the parent\n     * @param padding        the padding along the width for the parent\n     * @param childDimension the value of the child dimension\n     */\n    int getChildWidthMeasureSpec(int widthSpec, int padding, int childDimension);\n\n    /**\n     * Returns the child measure spec for its height.\n     *\n     * @param heightSpec     the measure spec for the height imposed by the parent\n     * @param padding        the padding along the height for the parent\n     * @param childDimension the value of the child dimension\n     */\n    int getChildHeightMeasureSpec(int heightSpec, int padding, int childDimension);\n\n    /**\n     * @return the largest main size of all flex lines including decorator lengths.\n     */\n    int getLargestMainSize();\n\n    /**\n     * @return the sum of the cross sizes of all flex lines including decorator lengths.\n     */\n    int getSumOfCrossSize();\n\n    /**\n     * Callback when a new flex item is added to the current container\n     *\n     * @param view            the view as a flex item which is added\n     * @param index           the absolute index of the flex item added\n     * @param indexInFlexLine the relative index of the flex item added within the flex line\n     * @param flexLine        the flex line where the new flex item is added\n     */\n    void onNewFlexItemAdded(View view, int index, int indexInFlexLine, FlexLine flexLine);\n\n    /**\n     * Callback when a new flex line is added to the current container\n     *\n     * @param flexLine the new added flex line\n     */\n    void onNewFlexLineAdded(FlexLine flexLine);\n\n    /**\n     * Sets the list of the flex lines that compose the flex container to the one received as an\n     * argument.\n     *\n     * @param flexLines the list of flex lines\n     */\n    void setFlexLines(List<FlexLine> flexLines);\n\n    /**\n     * @return the current value of the maximum number of flex lines. If not set, {@link #NOT_SET}\n     * is returned.\n     */\n    int getMaxLine();\n\n    /**\n     *\n     * @param maxLine the int value, which specifies the maximum number of flex lines\n     */\n    void setMaxLine(int maxLine);\n\n    /**\n     * @return the list of the flex lines including dummy flex lines (flex line that doesn't have\n     * any flex items in it but used for the alignment along the cross axis), which aren't included\n     * in the {@link FlexContainer#getFlexLines()}.\n     */\n    List<FlexLine> getFlexLinesInternal();\n\n    /**\n     * Update the view cache in the flex container.\n     *\n     * @param position the position of the view to be updated\n     * @param view     the view instance\n     */\n    void updateViewCache(int position, View view);\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexDirection.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport java.lang.annotation.Retention;\nimport java.lang.annotation.RetentionPolicy;\n\nimport androidx.annotation.IntDef;\n\n/**\n * The direction children items are placed inside the flex container, it determines the\n * direction of the main axis (and the cross axis, perpendicular to the main axis).\n */\n@IntDef({FlexDirection.ROW, FlexDirection.ROW_REVERSE, FlexDirection.COLUMN,\n        FlexDirection.COLUMN_REVERSE})\n@Retention(RetentionPolicy.SOURCE)\npublic @interface FlexDirection {\n\n    /**\n     * Main axis direction -> horizontal. Main start to\n     * main end -> Left to right (in LTR languages).\n     * Cross start to cross end -> Top to bottom\n     */\n    int ROW = 0;\n\n    /**\n     * Main axis direction -> horizontal. Main start\n     * to main end -> Right to left (in LTR languages). Cross start to cross end ->\n     * Top to bottom.\n     */\n    int ROW_REVERSE = 1;\n\n    /**\n     * Main axis direction -> vertical. Main start\n     * to main end -> Top to bottom. Cross start to cross end ->\n     * Left to right (In LTR languages).\n     */\n    int COLUMN = 2;\n\n    /**\n     * Main axis direction -> vertical. Main start\n     * to main end -> Bottom to top. Cross start to cross end -> Left to right\n     * (In LTR languages)\n     */\n    int COLUMN_REVERSE = 3;\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexItem.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport android.os.Parcelable;\nimport android.view.View;\n\n/**\n * An interface that has the common behavior as a flex item contained in a flex container.\n * Known classes that implement this interface are {@link FlexboxLayout.LayoutParams} and\n * {@link FlexboxLayoutManager.LayoutParams}.\n */\ninterface FlexItem extends Parcelable {\n\n    /** The default value for the order attribute */\n    int ORDER_DEFAULT = 1;\n\n    /** The default value for the flex grow attribute */\n    float FLEX_GROW_DEFAULT = 0f;\n\n    /** The default value for the flex shrink attribute */\n    float FLEX_SHRINK_DEFAULT = 1f;\n\n    /** The value representing the flex shrink attribute is not set  */\n    float FLEX_SHRINK_NOT_SET = 0f;\n\n    /** The default value for the flex basis percent attribute */\n    float FLEX_BASIS_PERCENT_DEFAULT = -1f;\n\n    /** The maximum size of the max width and max height attributes */\n    int MAX_SIZE = Integer.MAX_VALUE & View.MEASURED_SIZE_MASK;\n\n    /**\n     * @return the width attribute of the flex item.\n     *\n     * The attribute is about how wide the view wants to be. Can be one of the\n     * constants MATCH_PARENT(-1) or WRAP_CONTENT(-2), or an exact size.\n     */\n    int getWidth();\n\n    /**\n     * Sets the width attribute of the flex item.\n     *\n     * @param width the width attribute. Can be one of the\n     *              constants MATCH_PARENT(-1) or WRAP_CONTENT(-2), or an exact size.\n     */\n    void setWidth(int width);\n\n    /**\n     * @return the height attribute of the flex item.\n     *\n     * The attribute is about how wide the view wants to be. Can be one of the\n     * constants MATCH_PARENT(-1) or WRAP_CONTENT(-2), or an exact size.\n     */\n    int getHeight();\n\n    /**\n     * Sets the height attribute of the flex item.\n     *\n     * @param height the height attribute. Can be one of the\n     *               constants MATCH_PARENT(-1) or WRAP_CONTENT(-2), or an exact size.\n     */\n    void setHeight(int height);\n\n    /**\n     * @return the order attribute of the flex item.\n     *\n     * The attribute can change the ordering of the children views are laid out.\n     * By default, children are displayed and laid out in the same order as they appear in the\n     * layout XML. If not specified, {@link #ORDER_DEFAULT} is set as a default value.\n     */\n    int getOrder();\n\n    /**\n     * Sets the order attribute to the flex item\n     *\n     * @param order the order attribute\n     */\n    void setOrder(int order);\n\n    /**\n     * @return the flex grow attribute of the flex item\n     *\n     * The attribute determines how much this child will grow if positive free space is\n     * distributed relative to the rest of other flex items included in the same flex line.\n     * If not specified, {@link #FLEX_GROW_DEFAULT} is set as a default value.\n     */\n    float getFlexGrow();\n\n    /**\n     * Sets the flex grow attribute to the flex item\n     *\n     * @param flexGrow the flex grow attribute\n     */\n    void setFlexGrow(float flexGrow);\n\n    /**\n     * @return the flex shrink attribute of the flex item\n     *\n     * The attribute determines how much this child will shrink if negative free space is\n     * distributed relative to the rest of other flex items included in the same flex line.\n     * If not specified, {@link #FLEX_SHRINK_DEFAULT} is set as a default value.\n     */\n    float getFlexShrink();\n\n    /**\n     * Sets the flex shrink attribute to the flex item\n     *\n     * @param flexShrink the flex shrink attribute\n     */\n    void setFlexShrink(float flexShrink);\n\n    /**\n     * @return the align self attribute of the flex item\n     *\n     * The attribute determines the alignment along the cross axis (perpendicular to the\n     * main axis). The alignment in the same direction can be determined by the\n     * align items attribute in the parent, but if this is set to other than\n     * {@link AlignSelf#AUTO}, the cross axis alignment is overridden for this child.\n     * The value needs to be one of the values in ({@link AlignSelf#AUTO},\n     * {@link AlignItems#STRETCH}, {@link AlignItems#FLEX_START}, {@link\n     * AlignItems#FLEX_END}, {@link AlignItems#CENTER}, or {@link AlignItems#BASELINE}).\n     * If not specified, {@link AlignSelf#AUTO} is set as a default value.\n     */\n    @AlignSelf\n    int getAlignSelf();\n\n    /**\n     * Sets the align self attribute to the flex item\n     *\n     * @param alignSelf the order attribute\n     */\n    void setAlignSelf(@AlignSelf int alignSelf);\n\n    /**\n     * @return the minimum width attribute of the flex item\n     *\n     * The attribute determines the minimum width the child can shrink to.\n     */\n    int getMinWidth();\n\n    /**\n     * Sets the minimum width attribute to the flex item\n     *\n     * @param minWidth the order attribute\n     */\n    void setMinWidth(int minWidth);\n\n    /**\n     * @return the minimum height attribute of the flex item\n     *\n     * The attribute determines the minimum height the child can shrink to.\n     */\n    int getMinHeight();\n\n    /**\n     * Sets the minimum height attribute to the flex item\n     *\n     * @param minHeight the order attribute\n     */\n    void setMinHeight(int minHeight);\n\n    /**\n     * @return the maximum width attribute of the flex item\n     *\n     * The attribute determines the maximum width the child can expand to.\n     */\n    int getMaxWidth();\n\n    /**\n     * Sets the maximum width attribute to the flex item\n     *\n     * @param maxWidth the order attribute\n     */\n    void setMaxWidth(int maxWidth);\n\n    /**\n     * @return the maximum height attribute of the flex item\n     */\n    int getMaxHeight();\n\n    /**\n     * Sets the maximum height attribute to the flex item\n     *\n     * @param maxHeight the order attribute\n     */\n    void setMaxHeight(int maxHeight);\n\n    /**\n     * @return the wrapBefore attribute of the flex item\n     *\n     * The attribute forces a flex line wrapping. i.e. if this is set to {@code true} for a\n     * flex item, the item will become the first item of the new flex line. (A wrapping happens\n     * regardless of the flex items being processed in the the previous flex line)\n     * This attribute is ignored if the flex_wrap attribute is set as nowrap.\n     * The equivalent attribute isn't defined in the original CSS Flexible Box Module\n     * specification, but having this attribute is useful for Android developers to flatten\n     * the layouts when building a grid like layout or for a situation where developers want\n     * to put a new flex line to make a semantic difference from the previous one, etc.\n     */\n    boolean isWrapBefore();\n\n    /**\n     * Sets the wrapBefore attribute to the flex item\n     *\n     * @param wrapBefore the order attribute\n     */\n    void setWrapBefore(boolean wrapBefore);\n\n    /**\n     * @return the flexBasisPercent attribute of the flex item\n     *\n     * The attribute determines the initial flex item length in a fraction format relative to its\n     * parent.\n     * The initial main size of this child View is trying to be expanded as the specified\n     * fraction against the parent main size.\n     * If this value is set, the length specified from layout_width\n     * (or layout_height) is overridden by the calculated value from this attribute.\n     * This attribute is only effective when the parent's MeasureSpec mode is\n     * MeasureSpec.EXACTLY. The default value is -1, which means not set.\n     */\n    float getFlexBasisPercent();\n\n    /**\n     * Sets the flex basis percent attribute to the flex item\n     *\n     * @param flexBasisPercent the order attribute\n     */\n    void setFlexBasisPercent(float flexBasisPercent);\n\n    /**\n     * @return the left margin of the flex item.\n     */\n    int getMarginLeft();\n\n    /**\n     * @return the top margin of the flex item.\n     */\n    int getMarginTop();\n\n    /**\n     * @return the right margin of the flex item.\n     */\n    int getMarginRight();\n\n    /**\n     * @return the bottom margin of the flex item.\n     */\n    int getMarginBottom();\n\n    /**\n     * @return the start margin of the flex item depending on its resolved layout direction.\n     */\n    int getMarginStart();\n\n    /**\n     * @return the end margin of the flex item depending on its resolved layout direction.\n     */\n    int getMarginEnd();\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexLine.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport android.view.View;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\n/**\n * Holds properties related to a single flex line. This class is not expected to be changed outside\n * of the {@link FlexboxLayout}, thus only exposing the getter methods that may be useful for\n * other classes using the {@link FlexboxLayout}.\n */\npublic class FlexLine {\n\n    FlexLine() {\n    }\n\n    int mLeft = Integer.MAX_VALUE;\n\n    int mTop = Integer.MAX_VALUE;\n\n    int mRight = Integer.MIN_VALUE;\n\n    int mBottom = Integer.MIN_VALUE;\n\n    /** @see #getMainSize() */\n    int mMainSize;\n\n    /**\n     * The sum of the lengths of dividers along the main axis. This value should be lower\n     * than the value of {@link #mMainSize}.\n     */\n    int mDividerLengthInMainSize;\n\n    /** @see #getCrossSize() */\n    int mCrossSize;\n\n    /** @see #getItemCount() */\n    int mItemCount;\n\n    /** Holds the count of the views whose visibilities are gone */\n    int mGoneItemCount;\n\n    /** @see #getTotalFlexGrow() */\n    float mTotalFlexGrow;\n\n    /** @see #getTotalFlexShrink() */\n    float mTotalFlexShrink;\n\n    /**\n     * The largest value of the individual child's baseline (obtained by View#getBaseline()\n     * if the {@link FlexContainer#getAlignItems()} value is not {@link AlignItems#BASELINE}\n     * or the flex direction is vertical, this value is not used.\n     * If the alignment direction is from the bottom to top,\n     * (e.g. flexWrap == WRAP_REVERSE and flexDirection == ROW)\n     * store this value from the distance from the bottom of the view minus baseline.\n     * (Calculated as view.getMeasuredHeight() - view.getBaseline - LayoutParams.bottomMargin)\n     */\n    int mMaxBaseline;\n\n    /**\n     * The sum of the cross size used before this flex line.\n     */\n    int mSumCrossSizeBefore;\n\n    /**\n     * Store the indices of the children views whose alignSelf property is stretch.\n     * The stored indices are the absolute indices including all children in the Flexbox,\n     * not the relative indices in this flex line.\n     */\n    List<Integer> mIndicesAlignSelfStretch = new ArrayList<>();\n\n    int mFirstIndex;\n\n    int mLastIndex;\n\n    /**\n     * Set to true if any {@link FlexItem}s in this line have {@link FlexItem#getFlexGrow()}\n     * attributes set (have the value other than {@link FlexItem#FLEX_GROW_DEFAULT})\n     */\n    boolean mAnyItemsHaveFlexGrow;\n\n    /**\n     * Set to true if any {@link FlexItem}s in this line have {@link FlexItem#getFlexShrink()}\n     * attributes set (have the value other than {@link FlexItem#FLEX_SHRINK_NOT_SET})\n     */\n    boolean mAnyItemsHaveFlexShrink;\n\n    /**\n     * @return the size of the flex line in pixels along the main axis of the flex container.\n     */\n    public int getMainSize() {\n        return mMainSize;\n    }\n\n    /**\n     * @return the size of the flex line in pixels along the cross axis of the flex container.\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public int getCrossSize() {\n        return mCrossSize;\n    }\n\n    /**\n     * @return the count of the views contained in this flex line.\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public int getItemCount() {\n        return mItemCount;\n    }\n\n    /**\n     * @return the count of the views whose visibilities are not gone in this flex line.\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public int getItemCountNotGone() {\n        return mItemCount - mGoneItemCount;\n    }\n\n    /**\n     * @return the sum of the flexGrow properties of the children included in this flex line\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public float getTotalFlexGrow() {\n        return mTotalFlexGrow;\n    }\n\n    /**\n     * @return the sum of the flexShrink properties of the children included in this flex line\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public float getTotalFlexShrink() {\n        return mTotalFlexShrink;\n    }\n\n    /**\n     * @return the first view's index included in this flex line.\n     */\n    public int getFirstIndex() {\n        return mFirstIndex;\n    }\n\n    /**\n     * Updates the position of the flex line from the contained view.\n     *\n     * @param view             the view contained in this flex line\n     * @param leftDecoration   the length of the decoration on the left of the view\n     * @param topDecoration    the length of the decoration on the top of the view\n     * @param rightDecoration  the length of the decoration on the right of the view\n     * @param bottomDecoration the length of the decoration on the bottom of the view\n     */\n    void updatePositionFromView(View view, int leftDecoration, int topDecoration,\n            int rightDecoration, int bottomDecoration) {\n        FlexItem flexItem = (FlexItem) view.getLayoutParams();\n        mLeft = Math.min(mLeft, view.getLeft() - flexItem.getMarginLeft() - leftDecoration);\n        mTop = Math.min(mTop, view.getTop() - flexItem.getMarginTop() - topDecoration);\n        mRight = Math.max(mRight, view.getRight() + flexItem.getMarginRight() + rightDecoration);\n        mBottom = Math\n                .max(mBottom, view.getBottom() + flexItem.getMarginBottom() + bottomDecoration);\n    }\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexWrap.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport java.lang.annotation.Retention;\nimport java.lang.annotation.RetentionPolicy;\n\nimport androidx.annotation.IntDef;\n\n/**\n * This attribute controls whether the flex container is single-line or multi-line, and the\n * direction of the cross axis.\n */\n@IntDef({FlexWrap.NOWRAP, FlexWrap.WRAP, FlexWrap.WRAP_REVERSE})\n@Retention(RetentionPolicy.SOURCE)\npublic @interface FlexWrap {\n\n    /** The flex container is single-line. */\n    int NOWRAP = 0;\n\n    /** The flex container is multi-line. */\n    int WRAP = 1;\n\n    /**\n     * The flex container is multi-line. The direction of the\n     * cross axis is opposed to the direction as the {@link #WRAP}\n     */\n    int WRAP_REVERSE = 2;\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexboxHelper.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport static com.google.android.flexbox.FlexContainer.NOT_SET;\nimport static com.google.android.flexbox.FlexItem.FLEX_BASIS_PERCENT_DEFAULT;\nimport static com.google.android.flexbox.FlexItem.FLEX_GROW_DEFAULT;\nimport static com.google.android.flexbox.FlexItem.FLEX_SHRINK_NOT_SET;\n\nimport static androidx.recyclerview.widget.RecyclerView.NO_POSITION;\n\nimport android.graphics.drawable.Drawable;\nimport android.util.SparseIntArray;\nimport android.view.View;\nimport android.view.ViewGroup;\nimport android.widget.CompoundButton;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.Collections;\nimport java.util.List;\n\nimport androidx.annotation.NonNull;\nimport androidx.annotation.Nullable;\nimport androidx.annotation.VisibleForTesting;\nimport androidx.core.view.MarginLayoutParamsCompat;\nimport androidx.core.widget.CompoundButtonCompat;\n\n/**\n * Offers various calculations for Flexbox to use the common logic between the classes such as\n * {@link FlexboxLayout} and {@link FlexboxLayoutManager}.\n */\nclass FlexboxHelper {\n\n    private static final int INITIAL_CAPACITY = 10;\n\n    private static final long MEASURE_SPEC_WIDTH_MASK = 0xffffffffL;\n\n    private final FlexContainer mFlexContainer;\n\n    /**\n     * Holds the 'frozen' state of children during measure. If a view is frozen it will no longer\n     * expand or shrink regardless of flex grow/flex shrink attributes.\n     */\n    private boolean[] mChildrenFrozen;\n\n    /**\n     * Map the view index to the flex line which contains the view represented by the index to\n     * look for a flex line from a given view index in a constant time.\n     * Key: index of the view\n     * Value: index of the flex line that contains the given view\n     *\n     * E.g. if we have following flex lines,\n     * <p>\n     * FlexLine(0): itemCount 3\n     * FlexLine(1): itemCount 2\n     * </p>\n     * this instance should have following entries\n     * <p>\n     * [0, 0, 0, 1, 1, ...]\n     * </p>\n     */\n    @Nullable\n    int[] mIndexToFlexLine;\n\n    /**\n     * Cache the measured spec. The first 32 bit represents the height measure spec, the last\n     * 32 bit represents the width measure spec of each flex item.\n     * E.g. an entry is created like {@code (long) heightMeasureSpec << 32 | widthMeasureSpec}\n     *\n     * To retrieve a widthMeasureSpec, call {@link #extractLowerInt(long)} or\n     * {@link #extractHigherInt(long)} for a heightMeasureSpec.\n     */\n    @Nullable\n    long[] mMeasureSpecCache;\n\n    /**\n     * Cache a flex item's measured width and height. The first 32 bit represents the height, the\n     * last 32 bit represents the width of each flex item.\n     * E.g. an entry is created like the following code.\n     * {@code (long) view.getMeasuredHeight() << 32 | view.getMeasuredWidth()}\n     *\n     * To retrieve a width value, call {@link #extractLowerInt(long)} or\n     * {@link #extractHigherInt(long)} for a height value.\n     */\n    @Nullable\n    private long[] mMeasuredSizeCache;\n\n    FlexboxHelper(FlexContainer flexContainer) {\n        mFlexContainer = flexContainer;\n    }\n\n    /**\n     * Create an array, which indicates the reordered indices that\n     * {@link FlexItem#getOrder()} attributes are taken into account.\n     * This method takes a View before that is added as the parent ViewGroup's children.\n     *\n     * @param viewBeforeAdded          the View instance before added to the array of children\n     *                                 Views of the parent ViewGroup\n     * @param indexForViewBeforeAdded  the index for the View before added to the array of the\n     *                                 parent ViewGroup\n     * @param paramsForViewBeforeAdded the layout parameters for the View before added to the array\n     *                                 of the parent ViewGroup\n     * @return an array which have the reordered indices\n     */\n    int[] createReorderedIndices(View viewBeforeAdded, int indexForViewBeforeAdded,\n            ViewGroup.LayoutParams paramsForViewBeforeAdded, SparseIntArray orderCache) {\n        int childCount = mFlexContainer.getFlexItemCount();\n        List<Order> orders = createOrders(childCount);\n        Order orderForViewToBeAdded = new Order();\n        if (viewBeforeAdded != null\n                && paramsForViewBeforeAdded instanceof FlexItem) {\n            orderForViewToBeAdded.order = ((FlexItem)\n                    paramsForViewBeforeAdded).getOrder();\n        } else {\n            orderForViewToBeAdded.order = FlexItem.ORDER_DEFAULT;\n        }\n\n        if (indexForViewBeforeAdded == -1 || indexForViewBeforeAdded == childCount) {\n            orderForViewToBeAdded.index = childCount;\n        } else if (indexForViewBeforeAdded < mFlexContainer.getFlexItemCount()) {\n            orderForViewToBeAdded.index = indexForViewBeforeAdded;\n            for (int i = indexForViewBeforeAdded; i < childCount; i++) {\n                orders.get(i).index++;\n            }\n        } else {\n            // This path is not expected since OutOfBoundException will be thrown in the ViewGroup\n            // But setting the index for fail-safe\n            orderForViewToBeAdded.index = childCount;\n        }\n        orders.add(orderForViewToBeAdded);\n\n        return sortOrdersIntoReorderedIndices(childCount + 1, orders, orderCache);\n    }\n\n    /**\n     * Create an array, which indicates the reordered indices that\n     * {@link FlexItem#getOrder()} attributes are taken into account.\n     *\n     * @return @return an array which have the reordered indices\n     */\n    int[] createReorderedIndices(SparseIntArray orderCache) {\n        int childCount = mFlexContainer.getFlexItemCount();\n        List<Order> orders = createOrders(childCount);\n        return sortOrdersIntoReorderedIndices(childCount, orders, orderCache);\n    }\n\n    @NonNull\n    private List<Order> createOrders(int childCount) {\n        List<Order> orders = new ArrayList<>(childCount);\n        for (int i = 0; i < childCount; i++) {\n            View child = mFlexContainer.getFlexItemAt(i);\n            FlexItem flexItem = (FlexItem) child.getLayoutParams();\n            Order order = new Order();\n            order.order = flexItem.getOrder();\n            order.index = i;\n            orders.add(order);\n        }\n        return orders;\n    }\n\n    /**\n     * Returns if any of the children's {@link FlexItem#getOrder()} attributes are\n     * changed from the last measurement.\n     *\n     * @return {@code true} if changed from the last measurement, {@code false} otherwise.\n     */\n    boolean isOrderChangedFromLastMeasurement(SparseIntArray orderCache) {\n        int childCount = mFlexContainer.getFlexItemCount();\n        if (orderCache.size() != childCount) {\n            return true;\n        }\n        for (int i = 0; i < childCount; i++) {\n            View view = mFlexContainer.getFlexItemAt(i);\n            if (view == null) {\n                continue;\n            }\n            FlexItem flexItem = (FlexItem) view.getLayoutParams();\n            if (flexItem.getOrder() != orderCache.get(i)) {\n                return true;\n            }\n        }\n        return false;\n    }\n\n    private int[] sortOrdersIntoReorderedIndices(int childCount, List<Order> orders,\n            SparseIntArray orderCache) {\n        Collections.sort(orders);\n        orderCache.clear();\n        int[] reorderedIndices = new int[childCount];\n        int i = 0;\n        for (Order order : orders) {\n            reorderedIndices[i] = order.index;\n            orderCache.append(order.index, order.order);\n            i++;\n        }\n        return reorderedIndices;\n    }\n\n    /**\n     * Calculate how many flex lines are needed in the flex container.\n     * This method should calculate all the flex lines from the existing flex items.\n     *\n     * @see #calculateFlexLines(FlexLinesResult, int, int, int, int, int, List)\n     */\n    void calculateHorizontalFlexLines(FlexLinesResult result, int widthMeasureSpec,\n            int heightMeasureSpec) {\n        calculateFlexLines(result, widthMeasureSpec, heightMeasureSpec, Integer.MAX_VALUE,\n                0, NO_POSITION, null);\n    }\n\n    /**\n     * Calculate how many flex lines are needed in the flex container.\n     * Stop calculating it if the calculated amount along the cross size reaches the argument\n     * as the needsCalcAmount.\n     *\n     * @param result            an instance of {@link FlexLinesResult} that is going to contain a\n     *                          list of flex lines and the child state used by\n     *                          {@link View#setMeasuredDimension(int, int)}.\n     * @param widthMeasureSpec  the width measure spec imposed by the flex container\n     * @param heightMeasureSpec the height measure spec imposed by the flex container\n     * @param needsCalcAmount   the amount of pixels where flex line calculation should be stopped\n     *                          this is needed to avoid the expensive calculation if the\n     *                          calculation is needed only the small part of the entire flex\n     *                          container. (E.g. If the flex container is the\n     *                          {@link FlexboxLayoutManager}, the calculation only needs the\n     *                          visible area, imposing the entire calculation may cause bad\n     *                          performance\n     * @param fromIndex         the index of the child from which the calculation starts\n     * @param existingLines     If not null, calculated flex lines will be added to this instance\n     */\n    void calculateHorizontalFlexLines(FlexLinesResult result, int widthMeasureSpec,\n            int heightMeasureSpec, int needsCalcAmount, int fromIndex,\n            @Nullable List<FlexLine> existingLines) {\n        calculateFlexLines(result, widthMeasureSpec, heightMeasureSpec, needsCalcAmount,\n                fromIndex, NO_POSITION, existingLines);\n    }\n\n    /**\n     * Calculate how many flex lines are needed in the flex container.\n     * This method calculates the amount of pixels as the {@code needsCalcAmount} in addition to\n     * the\n     * flex lines which includes the view who has the index as the {@code toIndex} argument.\n     * (First calculate to the toIndex, then calculate the amount of pixels as needsCalcAmount)\n     *\n     * @param result            an instance of {@link FlexLinesResult} that is going to contain a\n     *                          list of flex lines and the child state used by\n     *                          {@link View#setMeasuredDimension(int, int)}.\n     * @param widthMeasureSpec  the width measure spec imposed by the flex container\n     * @param heightMeasureSpec the height measure spec imposed by the flex container\n     * @param needsCalcAmount   the amount of pixels where flex line calculation should be stopped\n     *                          this is needed to avoid the expensive calculation if the\n     *                          calculation is needed only the small part of the entire flex\n     *                          container. (E.g. If the flex container is the\n     *                          {@link FlexboxLayoutManager}, the calculation only needs the\n     *                          visible area, imposing the entire calculation may cause bad\n     *                          performance\n     * @param toIndex           the index of the child to which the calculation ends (until the\n     *                          flex line which include the which who has that index). If this\n     *                          and needsCalcAmount are both set, first flex lines are calculated\n     *                          to the index, calculate the amount of pixels as the needsCalcAmount\n     *                          argument in addition to that\n     */\n    void calculateHorizontalFlexLinesToIndex(FlexLinesResult result, int widthMeasureSpec,\n            int heightMeasureSpec, int needsCalcAmount, int toIndex, List<FlexLine> existingLines) {\n        calculateFlexLines(result, widthMeasureSpec, heightMeasureSpec, needsCalcAmount,\n                0, toIndex, existingLines);\n    }\n\n    /**\n     * Calculate how many flex lines are needed in the flex container.\n     * This method should calculate all the flex lines from the existing flex items.\n     *\n     * @param result            an instance of {@link FlexLinesResult} that is going to contain a\n     *                          list of flex lines and the child state used by\n     *                          {@link View#setMeasuredDimension(int, int)}.\n     * @param widthMeasureSpec  the width measure spec imposed by the flex container\n     * @param heightMeasureSpec the height measure spec imposed by the flex container\n     * @see #calculateFlexLines(FlexLinesResult, int, int, int, int, int, List)\n     */\n    void calculateVerticalFlexLines(FlexLinesResult result, int widthMeasureSpec, int heightMeasureSpec) {\n        calculateFlexLines(result, heightMeasureSpec, widthMeasureSpec, Integer.MAX_VALUE,\n                0, NO_POSITION, null);\n    }\n\n    /**\n     * Calculate how many flex lines are needed in the flex container.\n     * Stop calculating it if the calculated amount along the cross size reaches the argument\n     * as the needsCalcAmount.\n     *\n     * @param result            an instance of {@link FlexLinesResult} that is going to contain a\n     *                          list of flex lines and the child state used by\n     *                          {@link View#setMeasuredDimension(int, int)}.\n     * @param widthMeasureSpec  the width measure spec imposed by the flex container\n     * @param heightMeasureSpec the height measure spec imposed by the flex container\n     * @param needsCalcAmount   the amount of pixels where flex line calculation should be stopped\n     *                          this is needed to avoid the expensive calculation if the\n     *                          calculation is needed only the small part of the entire flex\n     *                          container. (E.g. If the flex container is the\n     *                          {@link FlexboxLayoutManager}, the calculation only needs the\n     *                          visible area, imposing the entire calculation may cause bad\n     *                          performance\n     * @param fromIndex         the index of the child from which the calculation starts\n     * @param existingLines     If not null, calculated flex lines will be added to this instance\n     */\n    void calculateVerticalFlexLines(FlexLinesResult result, int widthMeasureSpec,\n            int heightMeasureSpec, int needsCalcAmount, int fromIndex,\n            @Nullable List<FlexLine> existingLines) {\n        calculateFlexLines(result, heightMeasureSpec, widthMeasureSpec, needsCalcAmount,\n                fromIndex, NO_POSITION, existingLines);\n    }\n\n    /**\n     * Calculate how many flex lines are needed in the flex container.\n     * This method calculates the amount of pixels as the {@code needsCalcAmount} in addition to\n     * the\n     * flex lines which includes the view who has the index as the {@code toIndex} argument.\n     * (First calculate to the toIndex, then calculate the amount of pixels as needsCalcAmount)\n     *\n     * @param result            an instance of {@link FlexLinesResult} that is going to contain a\n     *                          list of flex lines and the child state used by\n     *                          {@link View#setMeasuredDimension(int, int)}.\n     * @param widthMeasureSpec  the width measure spec imposed by the flex container\n     * @param heightMeasureSpec the height measure spec imposed by the flex container\n     * @param needsCalcAmount   the amount of pixels where flex line calculation should be stopped\n     *                          this is needed to avoid the expensive calculation if the\n     *                          calculation is needed only the small part of the entire flex\n     *                          container. (E.g. If the flex container is the\n     *                          {@link FlexboxLayoutManager}, the calculation only needs the\n     *                          visible area, imposing the entire calculation may cause bad\n     *                          performance\n     * @param toIndex           the index of the child to which the calculation ends (until the\n     *                          flex line which include the which who has that index). If this\n     *                          and needsCalcAmount are both set, first flex lines are calculated\n     *                          to the index, calculate the amount of pixels as the needsCalcAmount\n     *                          argument in addition to that\n     */\n    void calculateVerticalFlexLinesToIndex(FlexLinesResult result, int widthMeasureSpec,\n            int heightMeasureSpec, int needsCalcAmount, int toIndex, List<FlexLine> existingLines) {\n        calculateFlexLines(result, heightMeasureSpec, widthMeasureSpec, needsCalcAmount,\n                0, toIndex, existingLines);\n    }\n\n\n    /**\n     * Calculates how many flex lines are needed in the flex container layout by measuring each\n     * child.\n     * Expanding or shrinking the flex items depending on the flex grow and flex shrink\n     * attributes are done in a later procedure, so the views' measured width and measured\n     * height may be changed in a later process.\n     *\n     * @param result           an instance of {@link FlexLinesResult} that is going to contain a\n     *                         list of flex lines and the child state used by\n     *                         {@link View#setMeasuredDimension(int, int)}.\n     * @param mainMeasureSpec  the main axis measure spec imposed by the flex container,\n     *                         width for horizontal direction, height otherwise\n     * @param crossMeasureSpec the cross axis measure spec imposed by the flex container,\n     *                         height for horizontal direction, width otherwise\n     * @param needsCalcAmount  the amount of pixels where flex line calculation should be stopped\n     *                         this is needed to avoid the expensive calculation if the\n     *                         calculation is needed only the small part of the entire flex\n     *                         container. (E.g. If the flex container is the\n     *                         {@link FlexboxLayoutManager}, the calculation only needs the\n     *                         visible area, imposing the entire calculation may cause bad\n     *                         performance\n     * @param fromIndex        the index of the child from which the calculation starts\n     * @param toIndex          the index of the child to which the calculation ends (until the\n     *                         flex line which include the which who has that index). If this\n     *                         and needsCalcAmount are both set, first flex lines are calculated\n     *                         to the index, calculate the amount of pixels as the needsCalcAmount\n     *                         argument in addition to that\n     * @param existingLines    If not null, calculated flex lines will be added to this instance\n     */\n    void calculateFlexLines(FlexLinesResult result, int mainMeasureSpec,\n            int crossMeasureSpec, int needsCalcAmount, int fromIndex, int toIndex,\n            @Nullable List<FlexLine> existingLines) {\n\n        boolean isMainHorizontal = mFlexContainer.isMainAxisDirectionHorizontal();\n\n        int mainMode = View.MeasureSpec.getMode(mainMeasureSpec);\n        int mainSize = View.MeasureSpec.getSize(mainMeasureSpec);\n\n        int childState = 0;\n\n        List<FlexLine> flexLines;\n        if (existingLines == null) {\n            flexLines = new ArrayList<>();\n        } else {\n            flexLines = existingLines;\n        }\n\n        result.mFlexLines = flexLines;\n\n        boolean reachedToIndex = toIndex == NO_POSITION;\n\n        int mainPaddingStart = getPaddingStartMain(isMainHorizontal);\n        int mainPaddingEnd = getPaddingEndMain(isMainHorizontal);\n        int crossPaddingStart = getPaddingStartCross(isMainHorizontal);\n        int crossPaddingEnd = getPaddingEndCross(isMainHorizontal);\n\n        int largestSizeInCross = Integer.MIN_VALUE;\n\n        // The amount of cross size calculated in this method call.\n        int sumCrossSize = 0;\n\n        // The index of the view in the flex line.\n        int indexInFlexLine = 0;\n\n        FlexLine flexLine = new FlexLine();\n        flexLine.mFirstIndex = fromIndex;\n        flexLine.mMainSize = mainPaddingStart + mainPaddingEnd;\n\n        int childCount = mFlexContainer.getFlexItemCount();\n        for (int i = fromIndex; i < childCount; i++) {\n            View child = mFlexContainer.getReorderedFlexItemAt(i);\n\n            if (child == null) {\n                if (isLastFlexItem(i, childCount, flexLine)) {\n                    addFlexLine(flexLines, flexLine, i, sumCrossSize);\n                }\n                continue;\n            } else if (child.getVisibility() == View.GONE) {\n                flexLine.mGoneItemCount++;\n                flexLine.mItemCount++;\n                if (isLastFlexItem(i, childCount, flexLine)) {\n                    addFlexLine(flexLines, flexLine, i, sumCrossSize);\n                }\n                continue;\n            } else if (child instanceof CompoundButton) {\n                evaluateMinimumSizeForCompoundButton((CompoundButton) child);\n            }\n\n            FlexItem flexItem = (FlexItem) child.getLayoutParams();\n\n            if (flexItem.getAlignSelf() == AlignItems.STRETCH) {\n                flexLine.mIndicesAlignSelfStretch.add(i);\n            }\n\n            int childMainSize = getFlexItemSizeMain(flexItem, isMainHorizontal);\n\n            if (flexItem.getFlexBasisPercent() != FLEX_BASIS_PERCENT_DEFAULT\n                    && mainMode == View.MeasureSpec.EXACTLY) {\n                childMainSize = Math.round(mainSize * flexItem.getFlexBasisPercent());\n                // Use the dimension from the layout if the mainMode is not\n                // MeasureSpec.EXACTLY even if any fraction value is set to\n                // layout_flexBasisPercent.\n            }\n\n            int childMainMeasureSpec;\n            int childCrossMeasureSpec;\n            if (isMainHorizontal) {\n                childMainMeasureSpec = mFlexContainer.getChildWidthMeasureSpec(mainMeasureSpec,\n                        mainPaddingStart + mainPaddingEnd +\n                                getFlexItemMarginStartMain(flexItem, true) +\n                                getFlexItemMarginEndMain(flexItem, true),\n                        childMainSize);\n                childCrossMeasureSpec = mFlexContainer.getChildHeightMeasureSpec(crossMeasureSpec,\n                        crossPaddingStart + crossPaddingEnd +\n                                getFlexItemMarginStartCross(flexItem, true) +\n                                getFlexItemMarginEndCross(flexItem, true)\n                                + sumCrossSize,\n                        getFlexItemSizeCross(flexItem, true));\n                child.measure(childMainMeasureSpec, childCrossMeasureSpec);\n                updateMeasureCache(i, childMainMeasureSpec, childCrossMeasureSpec, child);\n            } else {\n                childCrossMeasureSpec = mFlexContainer.getChildWidthMeasureSpec(crossMeasureSpec,\n                        crossPaddingStart + crossPaddingEnd +\n                                getFlexItemMarginStartCross(flexItem, false) +\n                                getFlexItemMarginEndCross(flexItem, false) + sumCrossSize,\n                        getFlexItemSizeCross(flexItem, false));\n                childMainMeasureSpec = mFlexContainer.getChildHeightMeasureSpec(mainMeasureSpec,\n                        mainPaddingStart + mainPaddingEnd +\n                                getFlexItemMarginStartMain(flexItem, false) +\n                                getFlexItemMarginEndMain(flexItem, false),\n                        childMainSize);\n                child.measure(childCrossMeasureSpec, childMainMeasureSpec);\n                updateMeasureCache(i, childCrossMeasureSpec, childMainMeasureSpec, child);\n            }\n            mFlexContainer.updateViewCache(i, child);\n\n            // Check the size constraint after the first measurement for the child\n            // To prevent the child's width/height violate the size constraints imposed by the\n            // {@link FlexItem#getMinWidth()}, {@link FlexItem#getMinHeight()},\n            // {@link FlexItem#getMaxWidth()} and {@link FlexItem#getMaxHeight()} attributes.\n            // E.g. When the child's layout_width is wrap_content the measured width may be\n            // less than the min width after the first measurement.\n            checkSizeConstraints(child, i);\n\n            childState = View.combineMeasuredStates(\n                    childState, child.getMeasuredState());\n\n            if (isWrapRequired(child, mainMode, mainSize, flexLine.mMainSize,\n                    getViewMeasuredSizeMain(child, isMainHorizontal)\n                            + getFlexItemMarginStartMain(flexItem, isMainHorizontal) +\n                            getFlexItemMarginEndMain(flexItem, isMainHorizontal),\n                    flexItem, i, indexInFlexLine, flexLines.size())) {\n                if (flexLine.getItemCountNotGone() > 0) {\n                    addFlexLine(flexLines, flexLine, i > 0 ? i - 1 : 0, sumCrossSize);\n                    sumCrossSize += flexLine.mCrossSize;\n                }\n\n                if (isMainHorizontal) {\n                    if (flexItem.getHeight() == ViewGroup.LayoutParams.MATCH_PARENT) {\n                        // This case takes care of the corner case where the cross size of the\n                        // child is affected by the just added flex line.\n                        // E.g. when the child's layout_height is set to match_parent, the height\n                        // of that child needs to be determined taking the total cross size used\n                        // so far into account. In that case, the height of the child needs to be\n                        // measured again note that we don't need to judge if the wrapping occurs\n                        // because it doesn't change the size along the main axis.\n                        childCrossMeasureSpec = mFlexContainer.getChildHeightMeasureSpec(\n                                crossMeasureSpec,\n                                mFlexContainer.getPaddingTop() + mFlexContainer.getPaddingBottom()\n                                        + flexItem.getMarginTop()\n                                        + flexItem.getMarginBottom() + sumCrossSize,\n                                flexItem.getHeight());\n                        child.measure(childMainMeasureSpec, childCrossMeasureSpec);\n                        checkSizeConstraints(child, i);\n                    }\n                } else {\n                    if (flexItem.getWidth() == ViewGroup.LayoutParams.MATCH_PARENT) {\n                        // This case takes care of the corner case where the cross size of the\n                        // child is affected by the just added flex line.\n                        // E.g. when the child's layout_width is set to match_parent, the width\n                        // of that child needs to be determined taking the total cross size used\n                        // so far into account. In that case, the width of the child needs to be\n                        // measured again note that we don't need to judge if the wrapping occurs\n                        // because it doesn't change the size along the main axis.\n                        childCrossMeasureSpec = mFlexContainer.getChildWidthMeasureSpec(\n                                crossMeasureSpec,\n                                mFlexContainer.getPaddingLeft() + mFlexContainer.getPaddingRight()\n                                        + flexItem.getMarginLeft()\n                                        + flexItem.getMarginRight() + sumCrossSize,\n                                flexItem.getWidth());\n                        child.measure(childCrossMeasureSpec, childMainMeasureSpec);\n                        checkSizeConstraints(child, i);\n                    }\n                }\n\n                flexLine = new FlexLine();\n                flexLine.mItemCount = 1;\n                flexLine.mMainSize = mainPaddingStart + mainPaddingEnd;\n                flexLine.mFirstIndex = i;\n                indexInFlexLine = 0;\n                largestSizeInCross = Integer.MIN_VALUE;\n            } else {\n                flexLine.mItemCount++;\n                indexInFlexLine++;\n            }\n            flexLine.mAnyItemsHaveFlexGrow |= flexItem.getFlexGrow() != FLEX_GROW_DEFAULT;\n            flexLine.mAnyItemsHaveFlexShrink |= flexItem.getFlexShrink() != FLEX_SHRINK_NOT_SET;\n\n            if (mIndexToFlexLine != null) {\n                mIndexToFlexLine[i] = flexLines.size();\n            }\n            flexLine.mMainSize += getViewMeasuredSizeMain(child, isMainHorizontal)\n                    + getFlexItemMarginStartMain(flexItem, isMainHorizontal) +\n                    getFlexItemMarginEndMain(flexItem, isMainHorizontal);\n            flexLine.mTotalFlexGrow += flexItem.getFlexGrow();\n            flexLine.mTotalFlexShrink += flexItem.getFlexShrink();\n\n            mFlexContainer.onNewFlexItemAdded(child, i, indexInFlexLine, flexLine);\n\n            largestSizeInCross = Math.max(largestSizeInCross,\n                    getViewMeasuredSizeCross(child, isMainHorizontal) +\n                            getFlexItemMarginStartCross(flexItem, isMainHorizontal) +\n                            getFlexItemMarginEndCross(flexItem, isMainHorizontal) +\n                            mFlexContainer.getDecorationLengthCrossAxis(child));\n            // Temporarily set the cross axis length as the largest child in the flexLine\n            // Expand along the cross axis depending on the mAlignContent property if needed\n            // later\n            flexLine.mCrossSize = Math.max(flexLine.mCrossSize, largestSizeInCross);\n\n            if (isMainHorizontal) {\n                if (mFlexContainer.getFlexWrap() != FlexWrap.WRAP_REVERSE) {\n                    flexLine.mMaxBaseline = Math.max(flexLine.mMaxBaseline,\n                            child.getBaseline() + flexItem.getMarginTop());\n                } else {\n                    // if the flex wrap property is WRAP_REVERSE, calculate the\n                    // baseline as the distance from the cross end and the baseline\n                    // since the cross size calculation is based on the distance from the cross end\n                    flexLine.mMaxBaseline = Math.max(flexLine.mMaxBaseline,\n                            child.getMeasuredHeight() - child.getBaseline()\n                                    + flexItem.getMarginBottom());\n                }\n            }\n\n            if (isLastFlexItem(i, childCount, flexLine)) {\n                addFlexLine(flexLines, flexLine, i, sumCrossSize);\n                sumCrossSize += flexLine.mCrossSize;\n            }\n\n            if (toIndex != NO_POSITION\n                    && flexLines.size() > 0\n                    && flexLines.get(flexLines.size() - 1).mLastIndex >= toIndex\n                    && i >= toIndex\n                    && !reachedToIndex) {\n                // Calculated to include a flex line which includes the flex item having the\n                // toIndex.\n                // Let the sumCrossSize start from the negative value of the last flex line's\n                // cross size because otherwise flex lines aren't calculated enough to fill the\n                // visible area.\n                sumCrossSize = -flexLine.getCrossSize();\n                reachedToIndex = true;\n            }\n            if (sumCrossSize > needsCalcAmount && reachedToIndex) {\n                // Stop the calculation if the sum of cross size calculated reached to the point\n                // beyond the needsCalcAmount value to avoid unneeded calculation in a\n                // RecyclerView.\n                // To be precise, the decoration length may be added to the sumCrossSize,\n                // but we omit adding the decoration length because even without the decorator\n                // length, it's guaranteed that calculation is done at least beyond the\n                // needsCalcAmount\n                break;\n            }\n        }\n\n        result.mChildState = childState;\n    }\n\n    /**\n     * Compound buttons (ex. {{@link android.widget.CheckBox}}, {@link android.widget.ToggleButton})\n     * have a button drawable with minimum height and width specified for them.\n     * To align the behavior with CSS Flexbox we want to respect these minimum measurement to avoid\n     * these drawables from being cut off during calculation. When the compound button has a minimum\n     * width or height already specified we will not make any change since we assume those were\n     * voluntarily set by the user.\n     *\n     * @param compoundButton the compound button that need to be evaluated\n     */\n    private void evaluateMinimumSizeForCompoundButton(CompoundButton compoundButton) {\n        FlexItem flexItem = (FlexItem) compoundButton.getLayoutParams();\n        int minWidth = flexItem.getMinWidth();\n        int minHeight = flexItem.getMinHeight();\n\n        Drawable drawable = CompoundButtonCompat.getButtonDrawable(compoundButton);\n        int drawableMinWidth = drawable == null ? 0 : drawable.getMinimumWidth();\n        int drawableMinHeight = drawable == null ? 0 : drawable.getMinimumHeight();\n        flexItem.setMinWidth(minWidth == NOT_SET ? drawableMinWidth : minWidth);\n        flexItem.setMinHeight(minHeight == NOT_SET ? drawableMinHeight : minHeight);\n    }\n\n    /**\n     * Returns the container's start padding in the main axis. Either start or top.\n     *\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the start padding in the main axis\n     */\n    private int getPaddingStartMain(boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return mFlexContainer.getPaddingStart();\n        }\n\n        return mFlexContainer.getPaddingTop();\n    }\n\n    /**\n     * Returns the container's end padding in the main axis. Either end or bottom.\n     *\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the end padding in the main axis\n     */\n    private int getPaddingEndMain(boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return mFlexContainer.getPaddingEnd();\n        }\n\n        return mFlexContainer.getPaddingBottom();\n    }\n\n    /**\n     * Returns the container's start padding in the cross axis. Either start or top.\n     *\n     * @param isMainHorizontal is the main axis horizontal.\n     * @return the start padding in the cross axis\n     */\n    private int getPaddingStartCross(boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return mFlexContainer.getPaddingTop();\n        }\n\n        return mFlexContainer.getPaddingStart();\n    }\n\n    /**\n     * Returns the container's end padding in the cross axis. Either end or bottom.\n     *\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the end padding in the cross axis\n     */\n    private int getPaddingEndCross(boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return mFlexContainer.getPaddingBottom();\n        }\n\n        return mFlexContainer.getPaddingEnd();\n    }\n\n    /**\n     * Returns the view's measured size in the main axis. Either width or height.\n     *\n     * @param view             the view\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the view's measured size in the main axis\n     */\n    private int getViewMeasuredSizeMain(View view, boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return view.getMeasuredWidth();\n        }\n\n        return view.getMeasuredHeight();\n    }\n\n    /**\n     * Returns the view's measured size in the cross axis. Either width or height.\n     *\n     * @param view             the view\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the view's measured size in the cross axis\n     */\n    private int getViewMeasuredSizeCross(View view, boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return view.getMeasuredHeight();\n        }\n\n        return view.getMeasuredWidth();\n    }\n\n    /**\n     * Returns the flexItem's size in the main axis. Either width or height.\n     *\n     * @param flexItem         the flexItem\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the flexItem's size in the main axis\n     */\n    private int getFlexItemSizeMain(FlexItem flexItem, boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return flexItem.getWidth();\n        }\n\n        return flexItem.getHeight();\n    }\n\n    /**\n     * Returns the flexItem's size in the cross axis. Either width or height.\n     *\n     * @param flexItem         the flexItem\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the flexItem's size in the cross axis\n     */\n    private int getFlexItemSizeCross(FlexItem flexItem, boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return flexItem.getHeight();\n        }\n\n        return flexItem.getWidth();\n    }\n\n    /**\n     * Returns the flexItem's start margin in the main axis. Either start or top.\n     * For the backward compatibility for API level < 17, the horizontal margin is returned using\n     * {@link FlexItem#getMarginLeft} (ViewGroup.MarginLayoutParams#getMarginStart isn't available\n     * in API level < 17). Thus this method needs to be used with {@link #getFlexItemMarginEndMain}\n     * not to misuse the margin in RTL.\n     *\n     *\n     * @param flexItem         the flexItem\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the flexItem's start margin in the main axis\n     */\n    private int getFlexItemMarginStartMain(FlexItem flexItem, boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return flexItem.getMarginLeft();\n        }\n\n        return flexItem.getMarginTop();\n    }\n\n    /**\n     * Returns the flexItem's end margin in the main axis. Either end or bottom.\n     * For the backward compatibility for API level < 17, the horizontal margin is returned using\n     * {@link FlexItem#getMarginRight} (ViewGroup.MarginLayoutParams#getMarginEnd isn't available\n     * in API level < 17). Thus this method needs to be used with\n     * {@link #getFlexItemMarginStartMain} not to misuse the margin in RTL.\n     *\n     * @param flexItem         the flexItem\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the flexItem's end margin in the main axis\n     */\n    private int getFlexItemMarginEndMain(FlexItem flexItem, boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return flexItem.getMarginRight();\n        }\n\n        return flexItem.getMarginBottom();\n    }\n\n    /**\n     * Returns the flexItem's start margin in the cross axis. Either start or top.\n     * For the backward compatibility for API level < 17, the horizontal margin is returned using\n     * {@link FlexItem#getMarginLeft} (ViewGroup.MarginLayoutParams#getMarginStart isn't available\n     * in API level < 17). Thus this method needs to be used with\n     * {@link #getFlexItemMarginEndCross} to not to misuse the margin in RTL.\n     *\n     * @param flexItem         the flexItem\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the flexItem's start margin in the cross axis\n     */\n    private int getFlexItemMarginStartCross(FlexItem flexItem, boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return flexItem.getMarginTop();\n        }\n\n        return flexItem.getMarginLeft();\n    }\n\n    /**\n     * Returns the flexItem's end margin in the cross axis. Either end or bottom.\n     * For the backward compatibility for API level < 17, the horizontal margin is returned using\n     * {@link FlexItem#getMarginRight} (ViewGroup.MarginLayoutParams#getMarginEnd isn't available\n     * in API level < 17). Thus this method needs to be used with\n     * {@link #getFlexItemMarginStartCross} to not to misuse the margin in RTL.\n     *\n     * @param flexItem         the flexItem\n     * @param isMainHorizontal is the main axis horizontal\n     * @return the flexItem's end margin in the cross axis\n     */\n    private int getFlexItemMarginEndCross(FlexItem flexItem, boolean isMainHorizontal) {\n        if (isMainHorizontal) {\n            return flexItem.getMarginBottom();\n        }\n\n        return flexItem.getMarginRight();\n    }\n\n    /**\n     * Determine if a wrap is required (add a new flex line).\n     *\n     * @param view          the view being judged if the wrap required\n     * @param mode          the width or height mode along the main axis direction\n     * @param maxSize       the max size along the main axis direction\n     * @param currentLength the accumulated current length\n     * @param childLength   the length of a child view which is to be collected to the flex line\n     * @param flexItem      the LayoutParams for the view being determined whether a new flex line\n     *                      is needed\n     * @param index         the index of the view being added within the entire flex container\n     * @param indexInFlexLine the index of the view being added within the current flex line\n     * @param flexLinesSize the number of the existing flexlines size\n     * @return {@code true} if a wrap is required, {@code false} otherwise\n     * @see FlexContainer#getFlexWrap()\n     * @see FlexContainer#setFlexWrap(int)\n     */\n    private boolean isWrapRequired(View view, int mode, int maxSize, int currentLength,\n            int childLength, FlexItem flexItem, int index, int indexInFlexLine, int flexLinesSize) {\n        if (mFlexContainer.getFlexWrap() == FlexWrap.NOWRAP) {\n            return false;\n        }\n        if (flexItem.isWrapBefore()) {\n            return true;\n        }\n        if (mode == View.MeasureSpec.UNSPECIFIED) {\n            return false;\n        }\n        int maxLine = mFlexContainer.getMaxLine();\n        // Judge the condition by adding 1 to the current flexLinesSize because the flex line\n        // being computed isn't added to the flexLinesSize.\n        if (maxLine != NOT_SET && maxLine <= flexLinesSize + 1) {\n            return false;\n        }\n        int decorationLength =\n                mFlexContainer.getDecorationLengthMainAxis(view, index, indexInFlexLine);\n        if (decorationLength > 0) {\n            childLength += decorationLength;\n        }\n        return maxSize < currentLength + childLength;\n    }\n\n    private boolean isLastFlexItem(int childIndex, int childCount,\n            FlexLine flexLine) {\n        return childIndex == childCount - 1 && flexLine.getItemCountNotGone() != 0;\n    }\n\n    private void addFlexLine(List<FlexLine> flexLines, FlexLine flexLine, int viewIndex,\n            int usedCrossSizeSoFar) {\n        flexLine.mSumCrossSizeBefore = usedCrossSizeSoFar;\n        mFlexContainer.onNewFlexLineAdded(flexLine);\n        flexLine.mLastIndex = viewIndex;\n        flexLines.add(flexLine);\n    }\n\n    /**\n     * Checks if the view's width/height don't violate the minimum/maximum size constraints imposed\n     * by the {@link FlexItem#getMinWidth()}, {@link FlexItem#getMinHeight()},\n     * {@link FlexItem#getMaxWidth()} and {@link FlexItem#getMaxHeight()} attributes.\n     *\n     * @param view  the view to be checked\n     * @param index index of the view\n     */\n    private void checkSizeConstraints(View view, int index) {\n        boolean needsMeasure = false;\n        FlexItem flexItem = (FlexItem) view.getLayoutParams();\n        int childWidth = view.getMeasuredWidth();\n        int childHeight = view.getMeasuredHeight();\n\n        if (childWidth < flexItem.getMinWidth()) {\n            needsMeasure = true;\n            childWidth = flexItem.getMinWidth();\n        } else if (childWidth > flexItem.getMaxWidth()) {\n            needsMeasure = true;\n            childWidth = flexItem.getMaxWidth();\n        }\n\n        if (childHeight < flexItem.getMinHeight()) {\n            needsMeasure = true;\n            childHeight = flexItem.getMinHeight();\n        } else if (childHeight > flexItem.getMaxHeight()) {\n            needsMeasure = true;\n            childHeight = flexItem.getMaxHeight();\n        }\n        if (needsMeasure) {\n            int widthSpec = View.MeasureSpec.makeMeasureSpec(childWidth, View.MeasureSpec.EXACTLY);\n            int heightSpec = View.MeasureSpec\n                    .makeMeasureSpec(childHeight, View.MeasureSpec.EXACTLY);\n            view.measure(widthSpec, heightSpec);\n            updateMeasureCache(index, widthSpec, heightSpec, view);\n            mFlexContainer.updateViewCache(index, view);\n        }\n    }\n\n    /**\n     * @see #determineMainSize(int, int, int)\n     */\n    void determineMainSize(int widthMeasureSpec, int heightMeasureSpec) {\n        determineMainSize(widthMeasureSpec, heightMeasureSpec, 0);\n    }\n\n    /**\n     * Determine the main size by expanding (shrinking if negative remaining free space is given)\n     * an individual child in each flex line if any children's mFlexGrow (or mFlexShrink if\n     * remaining\n     * space is negative) properties are set to non-zero.\n     *\n     * @param widthMeasureSpec  horizontal space requirements as imposed by the parent\n     * @param heightMeasureSpec vertical space requirements as imposed by the parent\n     * @see FlexContainer#setFlexDirection(int)\n     * @see FlexContainer#getFlexDirection()\n     */\n    void determineMainSize(int widthMeasureSpec, int heightMeasureSpec, int fromIndex) {\n        ensureChildrenFrozen(mFlexContainer.getFlexItemCount());\n        if (fromIndex >= mFlexContainer.getFlexItemCount()) {\n            return;\n        }\n        int mainSize;\n        int paddingAlongMainAxis;\n        int flexDirection = mFlexContainer.getFlexDirection();\n        switch (mFlexContainer.getFlexDirection()) {\n            case FlexDirection.ROW: // Intentional fall through\n            case FlexDirection.ROW_REVERSE:\n                int widthMode = View.MeasureSpec.getMode(widthMeasureSpec);\n                int widthSize = View.MeasureSpec.getSize(widthMeasureSpec);\n                int largestMainSize = mFlexContainer.getLargestMainSize();\n                if (widthMode == View.MeasureSpec.EXACTLY) {\n                    mainSize = widthSize;\n                } else {\n                    mainSize = Math.min(largestMainSize, widthSize);\n                }\n                paddingAlongMainAxis = mFlexContainer.getPaddingLeft()\n                        + mFlexContainer.getPaddingRight();\n                break;\n            case FlexDirection.COLUMN: // Intentional fall through\n            case FlexDirection.COLUMN_REVERSE:\n                int heightMode = View.MeasureSpec.getMode(heightMeasureSpec);\n                int heightSize = View.MeasureSpec.getSize(heightMeasureSpec);\n                if (heightMode == View.MeasureSpec.EXACTLY) {\n                    mainSize = heightSize;\n                } else {\n                    mainSize = mFlexContainer.getLargestMainSize();\n                }\n                paddingAlongMainAxis = mFlexContainer.getPaddingTop()\n                        + mFlexContainer.getPaddingBottom();\n                break;\n            default:\n                throw new IllegalArgumentException(\"Invalid flex direction: \" + flexDirection);\n        }\n\n        int flexLineIndex = 0;\n        if (mIndexToFlexLine != null) {\n            flexLineIndex = mIndexToFlexLine[fromIndex];\n        }\n        List<FlexLine> flexLines = mFlexContainer.getFlexLinesInternal();\n        for (int i = flexLineIndex, size = flexLines.size(); i < size; i++) {\n            FlexLine flexLine = flexLines.get(i);\n            if (flexLine.mMainSize < mainSize && flexLine.mAnyItemsHaveFlexGrow) {\n                expandFlexItems(widthMeasureSpec, heightMeasureSpec, flexLine,\n                        mainSize, paddingAlongMainAxis, false);\n            } else if (flexLine.mMainSize > mainSize && flexLine.mAnyItemsHaveFlexShrink) {\n                shrinkFlexItems(widthMeasureSpec, heightMeasureSpec, flexLine,\n                        mainSize, paddingAlongMainAxis, false);\n            }\n        }\n    }\n\n    private void ensureChildrenFrozen(int size) {\n        if (mChildrenFrozen == null) {\n            mChildrenFrozen = new boolean[Math.max(size, INITIAL_CAPACITY)];\n        } else if (mChildrenFrozen.length < size) {\n            int newCapacity = mChildrenFrozen.length * 2;\n            mChildrenFrozen = new boolean[Math.max(newCapacity, size)];\n        } else {\n            Arrays.fill(mChildrenFrozen, false);\n        }\n    }\n\n    /**\n     * Expand the flex items along the main axis based on the individual mFlexGrow attribute.\n     *\n     * @param widthMeasureSpec     the horizontal space requirements as imposed by the parent\n     * @param heightMeasureSpec    the vertical space requirements as imposed by the parent\n     * @param flexLine             the flex line to which flex items belong\n     * @param maxMainSize          the maximum main size. Expanded main size will be this size\n     * @param paddingAlongMainAxis the padding value along the main axis\n     * @param calledRecursively    true if this method is called recursively, false otherwise\n     * @see FlexContainer#getFlexDirection()\n     * @see FlexContainer#setFlexDirection(int)\n     * @see FlexItem#getFlexGrow()\n     */\n    private void expandFlexItems(int widthMeasureSpec, int heightMeasureSpec, FlexLine flexLine,\n            int maxMainSize, int paddingAlongMainAxis, boolean calledRecursively) {\n        if (flexLine.mTotalFlexGrow <= 0 || maxMainSize < flexLine.mMainSize) {\n            return;\n        }\n        int sizeBeforeExpand = flexLine.mMainSize;\n        boolean needsReexpand = false;\n        float unitSpace = (maxMainSize - flexLine.mMainSize) / flexLine.mTotalFlexGrow;\n        flexLine.mMainSize = paddingAlongMainAxis + flexLine.mDividerLengthInMainSize;\n\n        // Setting the cross size of the flex line as the temporal value since the cross size of\n        // each flex item may be changed from the initial calculation\n        // (in the measureHorizontal/measureVertical method) even this method is part of the main\n        // size determination.\n        // E.g. If a TextView's layout_width is set to 0dp, layout_height is set to wrap_content,\n        // and layout_flexGrow is set to 1, the TextView is trying to expand to the vertical\n        // direction to enclose its content (in the measureHorizontal method), but\n        // the width will be expanded in this method. In that case, the height needs to be measured\n        // again with the expanded width.\n        int largestCrossSize = 0;\n        if (!calledRecursively) {\n            flexLine.mCrossSize = Integer.MIN_VALUE;\n        }\n        float accumulatedRoundError = 0;\n        for (int i = 0; i < flexLine.mItemCount; i++) {\n            int index = flexLine.mFirstIndex + i;\n            View child = mFlexContainer.getReorderedFlexItemAt(index);\n            if (child == null || child.getVisibility() == View.GONE) {\n                continue;\n            }\n            FlexItem flexItem = (FlexItem) child.getLayoutParams();\n            int flexDirection = mFlexContainer.getFlexDirection();\n            if (flexDirection == FlexDirection.ROW || flexDirection == FlexDirection.ROW_REVERSE) {\n                // The direction of the main axis is horizontal\n\n                int childMeasuredWidth = child.getMeasuredWidth();\n                if (mMeasuredSizeCache != null) {\n                    // Retrieve the measured width from the cache because there\n                    // are some cases that the view is re-created from the last measure, thus\n                    // View#getMeasuredWidth returns 0.\n                    // E.g. if the flex container is FlexboxLayoutManager, the case happens\n                    // frequently\n                    childMeasuredWidth = extractLowerInt(mMeasuredSizeCache[index]);\n                }\n                int childMeasuredHeight = child.getMeasuredHeight();\n                if (mMeasuredSizeCache != null) {\n                    // Extract the measured height from the cache\n                    childMeasuredHeight = extractHigherInt(mMeasuredSizeCache[index]);\n                }\n                if (!mChildrenFrozen[index] && flexItem.getFlexGrow() > 0f) {\n                    float rawCalculatedWidth = childMeasuredWidth\n                            + unitSpace * flexItem.getFlexGrow();\n                    if (i == flexLine.mItemCount - 1) {\n                        rawCalculatedWidth += accumulatedRoundError;\n                        accumulatedRoundError = 0;\n                    }\n                    int newWidth = Math.round(rawCalculatedWidth);\n                    if (newWidth > flexItem.getMaxWidth()) {\n                        // This means the child can't expand beyond the value of the mMaxWidth\n                        // attribute.\n                        // To adjust the flex line length to the size of maxMainSize, remaining\n                        // positive free space needs to be re-distributed to other flex items\n                        // (children views). In that case, invoke this method again with the same\n                        // fromIndex.\n                        needsReexpand = true;\n                        newWidth = flexItem.getMaxWidth();\n                        mChildrenFrozen[index] = true;\n                        flexLine.mTotalFlexGrow -= flexItem.getFlexGrow();\n                    } else {\n                        accumulatedRoundError += (rawCalculatedWidth - newWidth);\n                        if (accumulatedRoundError > 1.0) {\n                            newWidth += 1;\n                            accumulatedRoundError -= 1.0;\n                        } else if (accumulatedRoundError < -1.0) {\n                            newWidth -= 1;\n                            accumulatedRoundError += 1.0;\n                        }\n                    }\n                    int childHeightMeasureSpec = getChildHeightMeasureSpecInternal(\n                            heightMeasureSpec, flexItem, flexLine.mSumCrossSizeBefore);\n                    int childWidthMeasureSpec = View.MeasureSpec.makeMeasureSpec(newWidth,\n                            View.MeasureSpec.EXACTLY);\n                    child.measure(childWidthMeasureSpec, childHeightMeasureSpec);\n                    childMeasuredWidth = child.getMeasuredWidth();\n                    childMeasuredHeight = child.getMeasuredHeight();\n                    updateMeasureCache(index, childWidthMeasureSpec, childHeightMeasureSpec,\n                            child);\n                    mFlexContainer.updateViewCache(index, child);\n                }\n                largestCrossSize = Math.max(largestCrossSize, childMeasuredHeight\n                        + flexItem.getMarginTop() + flexItem.getMarginBottom()\n                        + mFlexContainer.getDecorationLengthCrossAxis(child));\n                flexLine.mMainSize += childMeasuredWidth + flexItem.getMarginLeft()\n                        + flexItem.getMarginRight();\n            } else {\n                // The direction of the main axis is vertical\n\n                int childMeasuredHeight = child.getMeasuredHeight();\n                if (mMeasuredSizeCache != null) {\n                    // Retrieve the measured height from the cache because there\n                    // are some cases that the view is re-created from the last measure, thus\n                    // View#getMeasuredHeight returns 0.\n                    // E.g. if the flex container is FlexboxLayoutManager, that case happens\n                    // frequently\n                    childMeasuredHeight =\n                            extractHigherInt(mMeasuredSizeCache[index]);\n                }\n                int childMeasuredWidth = child.getMeasuredWidth();\n                if (mMeasuredSizeCache != null) {\n                    // Extract the measured width from the cache\n                    childMeasuredWidth =\n                            extractLowerInt(mMeasuredSizeCache[index]);\n                }\n                if (!mChildrenFrozen[index] && flexItem.getFlexGrow() > 0f) {\n                    float rawCalculatedHeight = childMeasuredHeight\n                            + unitSpace * flexItem.getFlexGrow();\n                    if (i == flexLine.mItemCount - 1) {\n                        rawCalculatedHeight += accumulatedRoundError;\n                        accumulatedRoundError = 0;\n                    }\n                    int newHeight = Math.round(rawCalculatedHeight);\n                    if (newHeight > flexItem.getMaxHeight()) {\n                        // This means the child can't expand beyond the value of the mMaxHeight\n                        // attribute.\n                        // To adjust the flex line length to the size of maxMainSize, remaining\n                        // positive free space needs to be re-distributed to other flex items\n                        // (children views). In that case, invoke this method again with the same\n                        // fromIndex.\n                        needsReexpand = true;\n                        newHeight = flexItem.getMaxHeight();\n                        mChildrenFrozen[index] = true;\n                        flexLine.mTotalFlexGrow -= flexItem.getFlexGrow();\n                    } else {\n                        accumulatedRoundError += (rawCalculatedHeight - newHeight);\n                        if (accumulatedRoundError > 1.0) {\n                            newHeight += 1;\n                            accumulatedRoundError -= 1.0;\n                        } else if (accumulatedRoundError < -1.0) {\n                            newHeight -= 1;\n                            accumulatedRoundError += 1.0;\n                        }\n                    }\n                    int childWidthMeasureSpec = getChildWidthMeasureSpecInternal(widthMeasureSpec,\n                            flexItem, flexLine.mSumCrossSizeBefore);\n                    int childHeightMeasureSpec = View.MeasureSpec.makeMeasureSpec(newHeight,\n                            View.MeasureSpec.EXACTLY);\n                    child.measure(childWidthMeasureSpec, childHeightMeasureSpec);\n                    childMeasuredWidth = child.getMeasuredWidth();\n                    childMeasuredHeight = child.getMeasuredHeight();\n                    updateMeasureCache(index, childWidthMeasureSpec, childHeightMeasureSpec,\n                            child);\n                    mFlexContainer.updateViewCache(index, child);\n                }\n                largestCrossSize = Math.max(largestCrossSize, childMeasuredWidth\n                        + flexItem.getMarginLeft() + flexItem.getMarginRight()\n                        + mFlexContainer.getDecorationLengthCrossAxis(child));\n                flexLine.mMainSize += childMeasuredHeight + flexItem.getMarginTop()\n                        + flexItem.getMarginBottom();\n            }\n            flexLine.mCrossSize = Math.max(flexLine.mCrossSize, largestCrossSize);\n        }\n\n        if (needsReexpand && sizeBeforeExpand != flexLine.mMainSize) {\n            // Re-invoke the method with the same flex line to distribute the positive free space\n            // that wasn't fully distributed (because of maximum length constraint)\n            expandFlexItems(widthMeasureSpec, heightMeasureSpec, flexLine, maxMainSize,\n                    paddingAlongMainAxis, true);\n        }\n    }\n\n    /**\n     * Shrink the flex items along the main axis based on the individual mFlexShrink attribute.\n     *\n     * @param widthMeasureSpec     the horizontal space requirements as imposed by the parent\n     * @param heightMeasureSpec    the vertical space requirements as imposed by the parent\n     * @param flexLine             the flex line to which flex items belong\n     * @param maxMainSize          the maximum main size. Shrank main size will be this size\n     * @param paddingAlongMainAxis the padding value along the main axis\n     * @param calledRecursively    true if this method is called recursively, false otherwise\n     * @see FlexContainer#getFlexDirection()\n     * @see FlexContainer#setFlexDirection(int)\n     * @see FlexItem#getFlexShrink()\n     */\n    private void shrinkFlexItems(int widthMeasureSpec, int heightMeasureSpec, FlexLine flexLine,\n            int maxMainSize, int paddingAlongMainAxis, boolean calledRecursively) {\n        int sizeBeforeShrink = flexLine.mMainSize;\n        if (flexLine.mTotalFlexShrink <= 0 || maxMainSize > flexLine.mMainSize) {\n            return;\n        }\n        boolean needsReshrink = false;\n        float unitShrink = (flexLine.mMainSize - maxMainSize) / flexLine.mTotalFlexShrink;\n        float accumulatedRoundError = 0;\n        flexLine.mMainSize = paddingAlongMainAxis + flexLine.mDividerLengthInMainSize;\n\n        // Setting the cross size of the flex line as the temporal value since the cross size of\n        // each flex item may be changed from the initial calculation\n        // (in the measureHorizontal/measureVertical method) even this method is part of the main\n        // size determination.\n        // E.g. If a TextView's layout_width is set to 0dp, layout_height is set to wrap_content,\n        // and layout_flexGrow is set to 1, the TextView is trying to expand to the vertical\n        // direction to enclose its content (in the measureHorizontal method), but\n        // the width will be expanded in this method. In that case, the height needs to be measured\n        // again with the expanded width.\n        int largestCrossSize = 0;\n        if (!calledRecursively) {\n            flexLine.mCrossSize = Integer.MIN_VALUE;\n        }\n        for (int i = 0; i < flexLine.mItemCount; i++) {\n            int index = flexLine.mFirstIndex + i;\n            View child = mFlexContainer.getReorderedFlexItemAt(index);\n            if (child == null || child.getVisibility() == View.GONE) {\n                continue;\n            }\n            FlexItem flexItem = (FlexItem) child.getLayoutParams();\n            int flexDirection = mFlexContainer.getFlexDirection();\n            if (flexDirection == FlexDirection.ROW || flexDirection == FlexDirection.ROW_REVERSE) {\n                // The direction of main axis is horizontal\n\n                int childMeasuredWidth = child.getMeasuredWidth();\n                if (mMeasuredSizeCache != null) {\n                    // Retrieve the measured width from the cache because there\n                    // are some cases that the view is re-created from the last measure, thus\n                    // View#getMeasuredWidth returns 0.\n                    // E.g. if the flex container is FlexboxLayoutManager, the case happens\n                    // frequently\n                    childMeasuredWidth = extractLowerInt(mMeasuredSizeCache[index]);\n                }\n                int childMeasuredHeight = child.getMeasuredHeight();\n                if (mMeasuredSizeCache != null) {\n                    // Extract the measured height from the cache\n                    childMeasuredHeight = extractHigherInt(mMeasuredSizeCache[index]);\n                }\n                if (!mChildrenFrozen[index] && flexItem.getFlexShrink() > 0f) {\n                    float rawCalculatedWidth = childMeasuredWidth\n                            - unitShrink * flexItem.getFlexShrink();\n                    if (i == flexLine.mItemCount - 1) {\n                        rawCalculatedWidth += accumulatedRoundError;\n                        accumulatedRoundError = 0;\n                    }\n                    int newWidth = Math.round(rawCalculatedWidth);\n                    if (newWidth < flexItem.getMinWidth()) {\n                        // This means the child doesn't have enough space to distribute the negative\n                        // free space. To adjust the flex line length down to the maxMainSize,\n                        // remaining\n                        // negative free space needs to be re-distributed to other flex items\n                        // (children views). In that case, invoke this method again with the same\n                        // fromIndex.\n                        needsReshrink = true;\n                        newWidth = flexItem.getMinWidth();\n                        mChildrenFrozen[index] = true;\n                        flexLine.mTotalFlexShrink -= flexItem.getFlexShrink();\n                    } else {\n                        accumulatedRoundError += (rawCalculatedWidth - newWidth);\n                        if (accumulatedRoundError > 1.0) {\n                            newWidth += 1;\n                            accumulatedRoundError -= 1;\n                        } else if (accumulatedRoundError < -1.0) {\n                            newWidth -= 1;\n                            accumulatedRoundError += 1;\n                        }\n                    }\n                    int childHeightMeasureSpec = getChildHeightMeasureSpecInternal(\n                            heightMeasureSpec, flexItem, flexLine.mSumCrossSizeBefore);\n                    int childWidthMeasureSpec =\n                            View.MeasureSpec.makeMeasureSpec(newWidth, View.MeasureSpec.EXACTLY);\n                    child.measure(childWidthMeasureSpec, childHeightMeasureSpec);\n\n                    childMeasuredWidth = child.getMeasuredWidth();\n                    childMeasuredHeight = child.getMeasuredHeight();\n                    updateMeasureCache(index, childWidthMeasureSpec, childHeightMeasureSpec,\n                            child);\n                    mFlexContainer.updateViewCache(index, child);\n                }\n                largestCrossSize = Math.max(largestCrossSize, childMeasuredHeight +\n                        flexItem.getMarginTop() + flexItem.getMarginBottom() +\n                        mFlexContainer.getDecorationLengthCrossAxis(child));\n                flexLine.mMainSize += childMeasuredWidth + flexItem.getMarginLeft()\n                        + flexItem.getMarginRight();\n            } else {\n                // The direction of main axis is vertical\n\n                int childMeasuredHeight = child.getMeasuredHeight();\n                if (mMeasuredSizeCache != null) {\n                    // Retrieve the measured height from the cache because there\n                    // are some cases that the view is re-created from the last measure, thus\n                    // View#getMeasuredHeight returns 0.\n                    // E.g. if the flex container is FlexboxLayoutManager, that case happens\n                    // frequently\n                    childMeasuredHeight =\n                            extractHigherInt(mMeasuredSizeCache[index]);\n                }\n                int childMeasuredWidth = child.getMeasuredWidth();\n                if (mMeasuredSizeCache != null) {\n                    // Extract the measured width from the cache\n                    childMeasuredWidth =\n                            extractLowerInt(mMeasuredSizeCache[index]);\n                }\n                if (!mChildrenFrozen[index] && flexItem.getFlexShrink() > 0f) {\n                    float rawCalculatedHeight = childMeasuredHeight\n                            - unitShrink * flexItem.getFlexShrink();\n                    if (i == flexLine.mItemCount - 1) {\n                        rawCalculatedHeight += accumulatedRoundError;\n                        accumulatedRoundError = 0;\n                    }\n                    int newHeight = Math.round(rawCalculatedHeight);\n                    if (newHeight < flexItem.getMinHeight()) {\n                        // Need to invoke this method again like the case flex direction is vertical\n                        needsReshrink = true;\n                        newHeight = flexItem.getMinHeight();\n                        mChildrenFrozen[index] = true;\n                        flexLine.mTotalFlexShrink -= flexItem.getFlexShrink();\n                    } else {\n                        accumulatedRoundError += (rawCalculatedHeight - newHeight);\n                        if (accumulatedRoundError > 1.0) {\n                            newHeight += 1;\n                            accumulatedRoundError -= 1;\n                        } else if (accumulatedRoundError < -1.0) {\n                            newHeight -= 1;\n                            accumulatedRoundError += 1;\n                        }\n                    }\n                    int childWidthMeasureSpec = getChildWidthMeasureSpecInternal(widthMeasureSpec,\n                            flexItem, flexLine.mSumCrossSizeBefore);\n                    int childHeightMeasureSpec =\n                            View.MeasureSpec.makeMeasureSpec(newHeight, View.MeasureSpec.EXACTLY);\n                    child.measure(childWidthMeasureSpec, childHeightMeasureSpec);\n\n                    childMeasuredWidth = child.getMeasuredWidth();\n                    childMeasuredHeight = child.getMeasuredHeight();\n                    updateMeasureCache(index, childWidthMeasureSpec, childHeightMeasureSpec,\n                            child);\n                    mFlexContainer.updateViewCache(index, child);\n                }\n                largestCrossSize = Math.max(largestCrossSize, childMeasuredWidth +\n                        flexItem.getMarginLeft() + flexItem.getMarginRight() +\n                        mFlexContainer.getDecorationLengthCrossAxis(child));\n                flexLine.mMainSize += childMeasuredHeight + flexItem.getMarginTop()\n                        + flexItem.getMarginBottom();\n            }\n            flexLine.mCrossSize = Math.max(flexLine.mCrossSize, largestCrossSize);\n        }\n\n        if (needsReshrink && sizeBeforeShrink != flexLine.mMainSize) {\n            // Re-invoke the method with the same fromIndex to distribute the negative free space\n            // that wasn't fully distributed (because some views length were not enough)\n            shrinkFlexItems(widthMeasureSpec, heightMeasureSpec, flexLine,\n                    maxMainSize, paddingAlongMainAxis, true);\n        }\n    }\n\n    private int getChildWidthMeasureSpecInternal(int widthMeasureSpec, FlexItem flexItem,\n            int padding) {\n        int childWidthMeasureSpec = mFlexContainer.getChildWidthMeasureSpec(widthMeasureSpec,\n                mFlexContainer.getPaddingLeft() + mFlexContainer.getPaddingRight() +\n                        flexItem.getMarginLeft() + flexItem.getMarginRight() + padding,\n                flexItem.getWidth());\n        int childWidth = View.MeasureSpec.getSize(childWidthMeasureSpec);\n        if (childWidth > flexItem.getMaxWidth()) {\n            childWidthMeasureSpec = View.MeasureSpec.makeMeasureSpec(flexItem.getMaxWidth(),\n                    View.MeasureSpec.getMode(childWidthMeasureSpec));\n        } else if (childWidth < flexItem.getMinWidth()) {\n            childWidthMeasureSpec = View.MeasureSpec.makeMeasureSpec(flexItem.getMinWidth(),\n                    View.MeasureSpec.getMode(childWidthMeasureSpec));\n        }\n        return childWidthMeasureSpec;\n    }\n\n    private int getChildHeightMeasureSpecInternal(int heightMeasureSpec, FlexItem flexItem,\n            int padding) {\n        int childHeightMeasureSpec = mFlexContainer.getChildHeightMeasureSpec(heightMeasureSpec,\n                mFlexContainer.getPaddingTop() + mFlexContainer.getPaddingBottom()\n                        + flexItem.getMarginTop() + flexItem.getMarginBottom() + padding,\n                flexItem.getHeight());\n        int childHeight = View.MeasureSpec.getSize(childHeightMeasureSpec);\n        if (childHeight > flexItem.getMaxHeight()) {\n            childHeightMeasureSpec = View.MeasureSpec.makeMeasureSpec(flexItem.getMaxHeight(),\n                    View.MeasureSpec.getMode(childHeightMeasureSpec));\n        } else if (childHeight < flexItem.getMinHeight()) {\n            childHeightMeasureSpec = View.MeasureSpec.makeMeasureSpec(flexItem.getMinHeight(),\n                    View.MeasureSpec.getMode(childHeightMeasureSpec));\n        }\n        return childHeightMeasureSpec;\n    }\n\n    /**\n     * Determines the cross size (Calculate the length along the cross axis).\n     * Expand the cross size only if the height mode is MeasureSpec.EXACTLY, otherwise\n     * use the sum of cross sizes of all flex lines.\n     *\n     * @param widthMeasureSpec      horizontal space requirements as imposed by the parent\n     * @param heightMeasureSpec     vertical space requirements as imposed by the parent\n     * @param paddingAlongCrossAxis the padding value for the FlexboxLayout along the cross axis\n     * @see FlexContainer#getFlexDirection()\n     * @see FlexContainer#setFlexDirection(int)\n     * @see FlexContainer#getAlignContent()\n     * @see FlexContainer#setAlignContent(int)\n     */\n    void determineCrossSize(int widthMeasureSpec, int heightMeasureSpec,\n            int paddingAlongCrossAxis) {\n        // The MeasureSpec mode along the cross axis\n        int mode;\n        // The MeasureSpec size along the cross axis\n        int size;\n        int flexDirection = mFlexContainer.getFlexDirection();\n        switch (flexDirection) {\n            case FlexDirection.ROW: // Intentional fall through\n            case FlexDirection.ROW_REVERSE:\n                mode = View.MeasureSpec.getMode(heightMeasureSpec);\n                size = View.MeasureSpec.getSize(heightMeasureSpec);\n                break;\n            case FlexDirection.COLUMN: // Intentional fall through\n            case FlexDirection.COLUMN_REVERSE:\n                mode = View.MeasureSpec.getMode(widthMeasureSpec);\n                size = View.MeasureSpec.getSize(widthMeasureSpec);\n                break;\n            default:\n                throw new IllegalArgumentException(\"Invalid flex direction: \" + flexDirection);\n        }\n        List<FlexLine> flexLines = mFlexContainer.getFlexLinesInternal();\n        if (mode == View.MeasureSpec.EXACTLY) {\n            int totalCrossSize = mFlexContainer.getSumOfCrossSize() + paddingAlongCrossAxis;\n            if (flexLines.size() == 1) {\n                flexLines.get(0).mCrossSize = size - paddingAlongCrossAxis;\n                // alignContent property is valid only if the Flexbox has at least two lines\n            } else if (flexLines.size() >= 2) {\n                switch (mFlexContainer.getAlignContent()) {\n                    case AlignContent.STRETCH: {\n                        if (totalCrossSize >= size) {\n                            break;\n                        }\n                        float freeSpaceUnit = (size - totalCrossSize) / (float) flexLines.size();\n                        float accumulatedError = 0;\n                        for (int i = 0, flexLinesSize = flexLines.size(); i < flexLinesSize; i++) {\n                            FlexLine flexLine = flexLines.get(i);\n                            float newCrossSizeAsFloat = flexLine.mCrossSize + freeSpaceUnit;\n                            if (i == flexLines.size() - 1) {\n                                newCrossSizeAsFloat += accumulatedError;\n                                accumulatedError = 0;\n                            }\n                            int newCrossSize = Math.round(newCrossSizeAsFloat);\n                            accumulatedError += (newCrossSizeAsFloat - newCrossSize);\n                            if (accumulatedError > 1) {\n                                newCrossSize += 1;\n                                accumulatedError -= 1;\n                            } else if (accumulatedError < -1) {\n                                newCrossSize -= 1;\n                                accumulatedError += 1;\n                            }\n                            flexLine.mCrossSize = newCrossSize;\n                        }\n                        break;\n                    }\n                    case AlignContent.SPACE_AROUND: {\n                        if (totalCrossSize >= size) {\n                            // If the size of the content is larger than the flex container, the\n                            // Flex lines should be aligned center like ALIGN_CONTENT_CENTER\n                            mFlexContainer.setFlexLines(\n                                    constructFlexLinesForAlignContentCenter(flexLines, size,\n                                            totalCrossSize));\n                            break;\n                        }\n                        // The value of free space along the cross axis which needs to be put on top\n                        // and below the bottom of each flex line.\n                        int spaceTopAndBottom = size - totalCrossSize;\n                        // The number of spaces along the cross axis\n                        int numberOfSpaces = flexLines.size() * 2;\n                        spaceTopAndBottom = spaceTopAndBottom / numberOfSpaces;\n                        List<FlexLine> newFlexLines = new ArrayList<>();\n                        FlexLine dummySpaceFlexLine = new FlexLine();\n                        dummySpaceFlexLine.mCrossSize = spaceTopAndBottom;\n                        for (FlexLine flexLine : flexLines) {\n                            newFlexLines.add(dummySpaceFlexLine);\n                            newFlexLines.add(flexLine);\n                            newFlexLines.add(dummySpaceFlexLine);\n                        }\n                        mFlexContainer.setFlexLines(newFlexLines);\n                        break;\n                    }\n                    case AlignContent.SPACE_BETWEEN: {\n                        if (totalCrossSize >= size) {\n                            break;\n                        }\n                        // The value of free space along the cross axis between each flex line.\n                        float spaceBetweenFlexLine = size - totalCrossSize;\n                        int numberOfSpaces = flexLines.size() - 1;\n                        spaceBetweenFlexLine = spaceBetweenFlexLine / (float) numberOfSpaces;\n                        float accumulatedError = 0;\n                        List<FlexLine> newFlexLines = new ArrayList<>();\n                        for (int i = 0, flexLineSize = flexLines.size(); i < flexLineSize; i++) {\n                            FlexLine flexLine = flexLines.get(i);\n                            newFlexLines.add(flexLine);\n\n                            if (i != flexLines.size() - 1) {\n                                FlexLine dummySpaceFlexLine = new FlexLine();\n                                if (i == flexLines.size() - 2) {\n                                    // The last dummy space block in the flex container.\n                                    // Adjust the cross size by the accumulated error.\n                                    dummySpaceFlexLine.mCrossSize = Math\n                                            .round(spaceBetweenFlexLine + accumulatedError);\n                                    accumulatedError = 0;\n                                } else {\n                                    dummySpaceFlexLine.mCrossSize = Math\n                                            .round(spaceBetweenFlexLine);\n                                }\n                                accumulatedError += (spaceBetweenFlexLine\n                                        - dummySpaceFlexLine.mCrossSize);\n                                if (accumulatedError > 1) {\n                                    dummySpaceFlexLine.mCrossSize += 1;\n                                    accumulatedError -= 1;\n                                } else if (accumulatedError < -1) {\n                                    dummySpaceFlexLine.mCrossSize -= 1;\n                                    accumulatedError += 1;\n                                }\n                                newFlexLines.add(dummySpaceFlexLine);\n                            }\n                        }\n                        mFlexContainer.setFlexLines(newFlexLines);\n                        break;\n                    }\n                    case AlignContent.CENTER: {\n                        mFlexContainer.setFlexLines(\n                                constructFlexLinesForAlignContentCenter(flexLines, size,\n                                        totalCrossSize));\n                        break;\n                    }\n                    case AlignContent.FLEX_END: {\n                        int spaceTop = size - totalCrossSize;\n                        FlexLine dummySpaceFlexLine = new FlexLine();\n                        dummySpaceFlexLine.mCrossSize = spaceTop;\n                        flexLines.add(0, dummySpaceFlexLine);\n                        break;\n                    }\n                    case AlignContent.FLEX_START:\n                        // No op. Just to cover the available switch statement options\n                        break;\n                }\n            }\n        }\n    }\n\n    private List<FlexLine> constructFlexLinesForAlignContentCenter(List<FlexLine> flexLines,\n            int size, int totalCrossSize) {\n        int spaceAboveAndBottom = size - totalCrossSize;\n        spaceAboveAndBottom = spaceAboveAndBottom / 2;\n        List<FlexLine> newFlexLines = new ArrayList<>();\n        FlexLine dummySpaceFlexLine = new FlexLine();\n        dummySpaceFlexLine.mCrossSize = spaceAboveAndBottom;\n        for (int i = 0, flexLineSize = flexLines.size(); i < flexLineSize; i++) {\n            if (i == 0) {\n                newFlexLines.add(dummySpaceFlexLine);\n            }\n            FlexLine flexLine = flexLines.get(i);\n            newFlexLines.add(flexLine);\n            if (i == flexLines.size() - 1) {\n                newFlexLines.add(dummySpaceFlexLine);\n            }\n        }\n        return newFlexLines;\n    }\n\n    void stretchViews() {\n        stretchViews(0);\n    }\n\n    /**\n     * Expand the view if the {@link FlexContainer#getAlignItems()} attribute is set to {@link\n     * AlignItems#STRETCH} or {@link FlexItem#getAlignSelf()} is set as\n     * {@link AlignItems#STRETCH}.\n     *\n     * @param fromIndex the index from which value, stretch is calculated\n     * @see FlexContainer#getFlexDirection()\n     * @see FlexContainer#setFlexDirection(int)\n     * @see FlexContainer#getAlignItems()\n     * @see FlexContainer#setAlignItems(int)\n     * @see FlexItem#getAlignSelf()\n     */\n    void stretchViews(int fromIndex) {\n        if (fromIndex >= mFlexContainer.getFlexItemCount()) {\n            return;\n        }\n        int flexDirection = mFlexContainer.getFlexDirection();\n        if (mFlexContainer.getAlignItems() == AlignItems.STRETCH) {\n            int flexLineIndex = 0;\n            if (mIndexToFlexLine != null) {\n                flexLineIndex = mIndexToFlexLine[fromIndex];\n            }\n            List<FlexLine> flexLines = mFlexContainer.getFlexLinesInternal();\n            for (int i = flexLineIndex, size = flexLines.size(); i < size; i++) {\n                FlexLine flexLine = flexLines.get(i);\n                for (int j = 0, itemCount = flexLine.mItemCount; j < itemCount; j++) {\n                    int viewIndex = flexLine.mFirstIndex + j;\n                    if (j >= mFlexContainer.getFlexItemCount()) {\n                        continue;\n                    }\n                    View view = mFlexContainer.getReorderedFlexItemAt(viewIndex);\n                    if (view == null || view.getVisibility() == View.GONE) {\n                        continue;\n                    }\n                    FlexItem flexItem = (FlexItem) view.getLayoutParams();\n                    if (flexItem.getAlignSelf() != AlignSelf.AUTO &&\n                            flexItem.getAlignSelf() != AlignItems.STRETCH) {\n                        continue;\n                    }\n                    switch (flexDirection) {\n                        case FlexDirection.ROW: // Intentional fall through\n                        case FlexDirection.ROW_REVERSE:\n                            stretchViewVertically(view, flexLine.mCrossSize, viewIndex);\n                            break;\n                        case FlexDirection.COLUMN:\n                        case FlexDirection.COLUMN_REVERSE:\n                            stretchViewHorizontally(view, flexLine.mCrossSize, viewIndex);\n                            break;\n                        default:\n                            throw new IllegalArgumentException(\n                                    \"Invalid flex direction: \" + flexDirection);\n                    }\n                }\n            }\n        } else {\n            for (FlexLine flexLine : mFlexContainer.getFlexLinesInternal()) {\n                for (Integer index : flexLine.mIndicesAlignSelfStretch) {\n                    View view = mFlexContainer.getReorderedFlexItemAt(index);\n                    switch (flexDirection) {\n                        case FlexDirection.ROW: // Intentional fall through\n                        case FlexDirection.ROW_REVERSE:\n                            stretchViewVertically(view, flexLine.mCrossSize, index);\n                            break;\n                        case FlexDirection.COLUMN:\n                        case FlexDirection.COLUMN_REVERSE:\n                            stretchViewHorizontally(view, flexLine.mCrossSize, index);\n                            break;\n                        default:\n                            throw new IllegalArgumentException(\n                                    \"Invalid flex direction: \" + flexDirection);\n                    }\n                }\n            }\n        }\n    }\n\n    /**\n     * Expand the view vertically to the size of the crossSize (considering the view margins)\n     *\n     * @param view      the View to be stretched\n     * @param crossSize the cross size\n     * @param index     the index of the view\n     */\n    private void stretchViewVertically(View view, int crossSize, int index) {\n        FlexItem flexItem = (FlexItem) view.getLayoutParams();\n        int newHeight = crossSize - flexItem.getMarginTop() - flexItem.getMarginBottom() -\n                mFlexContainer.getDecorationLengthCrossAxis(view);\n        newHeight = Math.max(newHeight, flexItem.getMinHeight());\n        newHeight = Math.min(newHeight, flexItem.getMaxHeight());\n        int childWidthSpec;\n        int measuredWidth;\n        if (mMeasuredSizeCache != null) {\n            // Retrieve the measured height from the cache because there\n            // are some cases that the view is re-created from the last measure, thus\n            // View#getMeasuredHeight returns 0.\n            // E.g. if the flex container is FlexboxLayoutManager, that case happens\n            // frequently\n            measuredWidth = extractLowerInt(mMeasuredSizeCache[index]);\n        } else {\n            measuredWidth = view.getMeasuredWidth();\n        }\n        childWidthSpec = View.MeasureSpec.makeMeasureSpec(measuredWidth,\n                View.MeasureSpec.EXACTLY);\n\n        int childHeightSpec = View.MeasureSpec.makeMeasureSpec(newHeight, View.MeasureSpec.EXACTLY);\n        view.measure(childWidthSpec, childHeightSpec);\n\n        updateMeasureCache(index, childWidthSpec, childHeightSpec, view);\n        mFlexContainer.updateViewCache(index, view);\n    }\n\n    /**\n     * Expand the view horizontally to the size of the crossSize (considering the view margins)\n     *\n     * @param view      the View to be stretched\n     * @param crossSize the cross size\n     * @param index     the index of the view\n     */\n    private void stretchViewHorizontally(View view, int crossSize, int index) {\n        FlexItem flexItem = (FlexItem) view.getLayoutParams();\n        int newWidth = crossSize - flexItem.getMarginLeft() - flexItem.getMarginRight()\n                - mFlexContainer.getDecorationLengthCrossAxis(view);\n        newWidth = Math.max(newWidth, flexItem.getMinWidth());\n        newWidth = Math.min(newWidth, flexItem.getMaxWidth());\n        int childHeightSpec;\n        int measuredHeight;\n        if (mMeasuredSizeCache != null) {\n            // Retrieve the measured height from the cache because there\n            // are some cases that the view is re-created from the last measure, thus\n            // View#getMeasuredHeight returns 0.\n            // E.g. if the flex container is FlexboxLayoutManager, that case happens\n            // frequently\n            measuredHeight = extractHigherInt(mMeasuredSizeCache[index]);\n        } else {\n            measuredHeight = view.getMeasuredHeight();\n        }\n        childHeightSpec = View.MeasureSpec.makeMeasureSpec(measuredHeight,\n                View.MeasureSpec.EXACTLY);\n        int childWidthSpec = View.MeasureSpec.makeMeasureSpec(newWidth, View.MeasureSpec.EXACTLY);\n        view.measure(childWidthSpec, childHeightSpec);\n\n        updateMeasureCache(index, childWidthSpec, childHeightSpec, view);\n        mFlexContainer.updateViewCache(index, view);\n    }\n\n    /**\n     * Place a single View when the layout direction is horizontal\n     * ({@link FlexContainer#getFlexDirection()} is either {@link FlexDirection#ROW} or\n     * {@link FlexDirection#ROW_REVERSE}).\n     *\n     * @param view     the View to be placed\n     * @param flexLine the {@link FlexLine} where the View belongs to\n     * @param left     the left position of the View, which the View's margin is already taken\n     *                 into account\n     * @param top      the top position of the flex line where the View belongs to. The actual\n     *                 View's top position is shifted depending on the flexWrap and alignItems\n     *                 attributes\n     * @param right    the right position of the View, which the View's margin is already taken\n     *                 into account\n     * @param bottom   the bottom position of the flex line where the View belongs to. The actual\n     *                 View's bottom position is shifted depending on the flexWrap and alignItems\n     *                 attributes\n     * @see FlexContainer#getAlignItems()\n     * @see FlexContainer#setAlignItems(int)\n     * @see FlexItem#getAlignSelf()\n     */\n    void layoutSingleChildHorizontal(View view, FlexLine flexLine, int left, int top, int right,\n            int bottom) {\n        FlexItem flexItem = (FlexItem) view.getLayoutParams();\n        int alignItems = mFlexContainer.getAlignItems();\n        if (flexItem.getAlignSelf() != AlignSelf.AUTO) {\n            // Expecting the values for alignItems and mAlignSelf match except for ALIGN_SELF_AUTO.\n            // Assigning the mAlignSelf value as alignItems should work.\n            alignItems = flexItem.getAlignSelf();\n        }\n        int crossSize = flexLine.mCrossSize;\n        switch (alignItems) {\n            case AlignItems.FLEX_START: // Intentional fall through\n            case AlignItems.STRETCH:\n                if (mFlexContainer.getFlexWrap() != FlexWrap.WRAP_REVERSE) {\n                    view.layout(left, top + flexItem.getMarginTop(), right,\n                            bottom + flexItem.getMarginTop());\n                } else {\n                    view.layout(left, top - flexItem.getMarginBottom(), right,\n                            bottom - flexItem.getMarginBottom());\n                }\n                break;\n            case AlignItems.BASELINE:\n                if (mFlexContainer.getFlexWrap() != FlexWrap.WRAP_REVERSE) {\n                    int marginTop = flexLine.mMaxBaseline - view.getBaseline();\n                    marginTop = Math.max(marginTop, flexItem.getMarginTop());\n                    view.layout(left, top + marginTop, right, bottom + marginTop);\n                } else {\n                    int marginBottom = flexLine.mMaxBaseline - view.getMeasuredHeight() + view\n                            .getBaseline();\n                    marginBottom = Math.max(marginBottom, flexItem.getMarginBottom());\n                    view.layout(left, top - marginBottom, right, bottom - marginBottom);\n                }\n                break;\n            case AlignItems.FLEX_END:\n                if (mFlexContainer.getFlexWrap() != FlexWrap.WRAP_REVERSE) {\n                    view.layout(left,\n                            top + crossSize - view.getMeasuredHeight() - flexItem.getMarginBottom(),\n                            right, top + crossSize - flexItem.getMarginBottom());\n                } else {\n                    // If the flexWrap == WRAP_REVERSE, the direction of the\n                    // flexEnd is flipped (from top to bottom).\n                    view.layout(left,\n                            top - crossSize + view.getMeasuredHeight() + flexItem.getMarginTop(),\n                            right, bottom - crossSize + view.getMeasuredHeight() + flexItem\n                                    .getMarginTop());\n                }\n                break;\n            case AlignItems.CENTER:\n                int topFromCrossAxis = (crossSize - view.getMeasuredHeight()\n                        + flexItem.getMarginTop() - flexItem.getMarginBottom()) / 2;\n                if (mFlexContainer.getFlexWrap() != FlexWrap.WRAP_REVERSE) {\n                    view.layout(left, top + topFromCrossAxis,\n                            right, top + topFromCrossAxis + view.getMeasuredHeight());\n                } else {\n                    view.layout(left, top - topFromCrossAxis,\n                            right, top - topFromCrossAxis + view.getMeasuredHeight());\n                }\n                break;\n        }\n    }\n\n    /**\n     * Place a single View when the layout direction is vertical\n     * ({@link FlexContainer#getFlexDirection()} is either {@link FlexDirection#COLUMN} or\n     * {@link FlexDirection#COLUMN_REVERSE}).\n     *\n     * @param view     the View to be placed\n     * @param flexLine the {@link FlexLine} where the View belongs to\n     * @param isRtl    {@code true} if the layout direction is right to left, {@code false}\n     *                 otherwise\n     * @param left     the left position of the flex line where the View belongs to. The actual\n     *                 View's left position is shifted depending on the isLayoutRtl and alignItems\n     *                 attributes\n     * @param top      the top position of the View, which the View's margin is already taken\n     *                 into account\n     * @param right    the right position of the flex line where the View belongs to. The actual\n     *                 View's right position is shifted depending on the isLayoutRtl and alignItems\n     *                 attributes\n     * @param bottom   the bottom position of the View, which the View's margin is already taken\n     *                 into account\n     * @see FlexContainer#getAlignItems()\n     * @see FlexContainer#setAlignItems(int)\n     * @see FlexItem#getAlignSelf()\n     */\n    void layoutSingleChildVertical(View view, FlexLine flexLine, boolean isRtl,\n            int left, int top, int right, int bottom) {\n        FlexItem flexItem = (FlexItem) view.getLayoutParams();\n        int alignItems = mFlexContainer.getAlignItems();\n        if (flexItem.getAlignSelf() != AlignSelf.AUTO) {\n            // Expecting the values for alignItems and mAlignSelf match except for ALIGN_SELF_AUTO.\n            // Assigning the mAlignSelf value as alignItems should work.\n            alignItems = flexItem.getAlignSelf();\n        }\n        int crossSize = flexLine.mCrossSize;\n        switch (alignItems) {\n            case AlignItems.FLEX_START: // Intentional fall through\n            case AlignItems.STRETCH: // Intentional fall through\n            case AlignItems.BASELINE:\n                if (!isRtl) {\n                    view.layout(left + flexItem.getMarginLeft(), top,\n                            right + flexItem.getMarginLeft(), bottom);\n                } else {\n                    view.layout(left - flexItem.getMarginRight(), top,\n                            right - flexItem.getMarginRight(), bottom);\n                }\n                break;\n            case AlignItems.FLEX_END:\n                if (!isRtl) {\n                    view.layout(\n                            left + crossSize - view.getMeasuredWidth() - flexItem.getMarginRight(),\n                            top,\n                            right + crossSize - view.getMeasuredWidth() - flexItem.getMarginRight(),\n                            bottom);\n                } else {\n                    // If the flexWrap == WRAP_REVERSE, the direction of the\n                    // flexEnd is flipped (from left to right).\n                    view.layout(\n                            left - crossSize + view.getMeasuredWidth() + flexItem.getMarginLeft(),\n                            top,\n                            right - crossSize + view.getMeasuredWidth() + flexItem.getMarginLeft(),\n                            bottom);\n                }\n                break;\n            case AlignItems.CENTER:\n                ViewGroup.MarginLayoutParams lp = (ViewGroup.MarginLayoutParams)\n                        view.getLayoutParams();\n                int leftFromCrossAxis = (crossSize - view.getMeasuredWidth()\n                        + MarginLayoutParamsCompat.getMarginStart(lp)\n                        - MarginLayoutParamsCompat.getMarginEnd(lp)) / 2;\n                if (!isRtl) {\n                    view.layout(left + leftFromCrossAxis, top, right + leftFromCrossAxis, bottom);\n                } else {\n                    view.layout(left - leftFromCrossAxis, top, right - leftFromCrossAxis, bottom);\n                }\n                break;\n        }\n    }\n\n    void ensureMeasuredSizeCache(int size) {\n        if (mMeasuredSizeCache == null) {\n            mMeasuredSizeCache = new long[Math.max(size, INITIAL_CAPACITY)];\n        } else if (mMeasuredSizeCache.length < size) {\n            int newCapacity = mMeasuredSizeCache.length * 2;\n            newCapacity = Math.max(newCapacity, size);\n            mMeasuredSizeCache = Arrays.copyOf(mMeasuredSizeCache, newCapacity);\n        }\n    }\n\n    void ensureMeasureSpecCache(int size) {\n        if (mMeasureSpecCache == null) {\n            mMeasureSpecCache = new long[Math.max(size, INITIAL_CAPACITY)];\n        } else if (mMeasureSpecCache.length < size) {\n            int newCapacity = mMeasureSpecCache.length * 2;\n            newCapacity = Math.max(newCapacity, size);\n            mMeasureSpecCache = Arrays.copyOf(mMeasureSpecCache, newCapacity);\n        }\n    }\n\n    /**\n     * @param longValue the long value that consists of width and height measure specs\n     * @return the int value which consists from the lower 8 bits\n     * @see #makeCombinedLong(int, int)\n     */\n    int extractLowerInt(long longValue) {\n        return (int) longValue;\n    }\n\n    /**\n     * @param longValue the long value that consists of width and height measure specs\n     * @return the int value which consists from the higher 8 bits\n     * @see #makeCombinedLong(int, int)\n     */\n    int extractHigherInt(long longValue) {\n        return (int) (longValue >> 32);\n    }\n\n    /**\n     * Make a long value from the a width measure spec and a height measure spec.\n     * The first 32 bit is used for the height measure spec and the last 32 bit is used for the\n     * width measure spec.\n     *\n     * @param widthMeasureSpec  the width measure spec to consist the result long value\n     * @param heightMeasureSpec the height measure spec to consist the result long value\n     * @return the combined long value\n     * @see #extractLowerInt(long)\n     * @see #extractHigherInt(long)\n     */\n    @VisibleForTesting\n    long makeCombinedLong(int widthMeasureSpec, int heightMeasureSpec) {\n        // Suppress sign extension for the low bytes\n        return (long) heightMeasureSpec << 32 | (long) widthMeasureSpec & MEASURE_SPEC_WIDTH_MASK;\n    }\n\n    private void updateMeasureCache(int index, int widthMeasureSpec, int heightMeasureSpec,\n            View view) {\n        if (mMeasureSpecCache != null) {\n            mMeasureSpecCache[index] = makeCombinedLong(\n                    widthMeasureSpec,\n                    heightMeasureSpec);\n        }\n        if (mMeasuredSizeCache != null) {\n            mMeasuredSizeCache[index] = makeCombinedLong(\n                    view.getMeasuredWidth(),\n                    view.getMeasuredHeight());\n        }\n    }\n\n    void ensureIndexToFlexLine(int size) {\n        if (mIndexToFlexLine == null) {\n            mIndexToFlexLine = new int[Math.max(size, INITIAL_CAPACITY)];\n        } else if (mIndexToFlexLine.length < size) {\n            int newCapacity = mIndexToFlexLine.length * 2;\n            newCapacity = Math.max(newCapacity, size);\n            mIndexToFlexLine = Arrays.copyOf(mIndexToFlexLine, newCapacity);\n        }\n    }\n\n    /**\n     * Clear the from flex lines and the caches from the index passed as an argument.\n     *\n     * @param flexLines    the flex lines to be cleared\n     * @param fromFlexItem the index from which, flex lines are cleared\n     */\n    void clearFlexLines(List<FlexLine> flexLines, int fromFlexItem) {\n        assert mIndexToFlexLine != null;\n        assert mMeasureSpecCache != null;\n\n        int fromFlexLine = mIndexToFlexLine[fromFlexItem];\n        if (fromFlexLine == NO_POSITION) {\n            fromFlexLine = 0;\n        }\n\n        // Deleting from the last to avoid unneeded copy it happens when deleting the middle of the\n        // item in the ArrayList\n        if (flexLines.size() > fromFlexLine) {\n            flexLines.subList(fromFlexLine, flexLines.size()).clear();\n        }\n\n        int fillTo = mIndexToFlexLine.length - 1;\n        if (fromFlexItem > fillTo) {\n            Arrays.fill(mIndexToFlexLine, NO_POSITION);\n        } else {\n            Arrays.fill(mIndexToFlexLine, fromFlexItem, fillTo, NO_POSITION);\n        }\n\n        fillTo = mMeasureSpecCache.length - 1;\n        if (fromFlexItem > fillTo) {\n            Arrays.fill(mMeasureSpecCache, 0);\n        } else {\n            Arrays.fill(mMeasureSpecCache, fromFlexItem, fillTo, 0);\n        }\n    }\n\n    /**\n     * A class that is used for calculating the view order which view's indices and order\n     * properties from Flexbox are taken into account.\n     */\n    private static class Order implements Comparable<Order> {\n\n        /** {@link View}'s index */\n        int index;\n\n        /** order property in the Flexbox */\n        int order;\n\n        @Override\n        public int compareTo(@NonNull Order another) {\n            if (order != another.order) {\n                return order - another.order;\n            }\n            return index - another.index;\n        }\n\n        @NonNull\n        @Override\n        public String toString() {\n            return \"Order{\" +\n                    \"order=\" + order +\n                    \", index=\" + index +\n                    '}';\n        }\n    }\n\n    static class FlexLinesResult {\n\n        List<FlexLine> mFlexLines;\n\n        int mChildState;\n\n        void reset() {\n            mFlexLines = null;\n            mChildState = 0;\n        }\n    }\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexboxItemDecoration.java",
    "content": "/*\n * Copyright 2017 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport static androidx.recyclerview.widget.RecyclerView.NO_POSITION;\n\nimport android.content.Context;\nimport android.content.res.TypedArray;\nimport android.graphics.Canvas;\nimport android.graphics.Rect;\nimport android.graphics.drawable.Drawable;\nimport android.view.View;\n\nimport java.util.List;\n\nimport androidx.annotation.NonNull;\nimport androidx.recyclerview.widget.RecyclerView;\n\n/**\n * {@link RecyclerView.ItemDecoration} implementation that can be used as item decorations between\n * view holders within the {@link FlexboxLayoutManager}.\n *\n * Orientation for the decoration can be either of:\n * <ul>\n * <li>Horizontal (setOrientation(HORIZONTAL)</li>\n * <li>Vertical (setOrientation(VERTICAL)</li>\n * <li>Both orientation (setOrientation(BOTH)</li>\n * </ul>.\n * The default value is set to both.\n */\npublic class FlexboxItemDecoration extends RecyclerView.ItemDecoration {\n\n    public static final int HORIZONTAL = 1;\n    public static final int VERTICAL = 1 << 1;\n    @SuppressWarnings(\"WeakerAccess\")\n    public static final int BOTH = HORIZONTAL | VERTICAL;\n\n    private static final int[] LIST_DIVIDER_ATTRS = new int[]{android.R.attr.listDivider};\n\n    private Drawable mDrawable;\n\n    private int mOrientation;\n\n    public FlexboxItemDecoration(Context context) {\n        final TypedArray a = context.obtainStyledAttributes(LIST_DIVIDER_ATTRS);\n        mDrawable = a.getDrawable(0);\n        a.recycle();\n        setOrientation(BOTH);\n    }\n\n    /**\n     * Set the drawable used as the item decoration.\n     * If the drawable is not set, the default list divider is used as the\n     * item decoration.\n     */\n    public void setDrawable(Drawable drawable) {\n        if (drawable == null) {\n            throw new IllegalArgumentException(\"Drawable cannot be null.\");\n        }\n        mDrawable = drawable;\n    }\n\n    /**\n     * Set the orientation for the decoration.\n     * Orientation for the decoration can be either of:\n     * <ul>\n     * <li>Horizontal (setOrientation(HORIZONTAL)</li>\n     * <li>Vertical (setOrientation(VERTICAL)</li>\n     * <li>Both orientation (setOrientation(BOTH)</li>\n     * </ul>.\n     */\n    public void setOrientation(int orientation) {\n        mOrientation = orientation;\n    }\n\n    @Override\n    public void onDraw(\n            @NonNull Canvas canvas,\n            @NonNull RecyclerView parent,\n            @NonNull RecyclerView.State state) {\n        drawHorizontalDecorations(canvas, parent);\n        drawVerticalDecorations(canvas, parent);\n    }\n\n    @Override\n    public void getItemOffsets(\n            @NonNull Rect outRect,\n            @NonNull View view,\n            RecyclerView parent,\n            @NonNull RecyclerView.State state) {\n        int position = parent.getChildAdapterPosition(view);\n        if (position == 0) {\n            return;\n        }\n        if (!needsHorizontalDecoration() && !needsVerticalDecoration()) {\n            outRect.set(0, 0, 0, 0);\n            return;\n        }\n        FlexboxLayoutManager layoutManager = (FlexboxLayoutManager) parent.getLayoutManager();\n        List<FlexLine> flexLines = layoutManager.getFlexLines();\n        int flexDirection = layoutManager.getFlexDirection();\n        setOffsetAlongMainAxis(outRect, position, layoutManager, flexLines, flexDirection);\n        setOffsetAlongCrossAxis(outRect, position, layoutManager, flexLines);\n    }\n\n    private void setOffsetAlongCrossAxis(Rect outRect, int position,\n            FlexboxLayoutManager layoutManager, List<FlexLine> flexLines) {\n        if (flexLines.size() == 0) {\n            return;\n        }\n        int flexLineIndex = layoutManager.getPositionToFlexLineIndex(position);\n        if (flexLineIndex == 0) {\n            return;\n        }\n\n        if (layoutManager.isMainAxisDirectionHorizontal()) {\n            if (!needsHorizontalDecoration()) {\n                outRect.top = 0;\n                outRect.bottom = 0;\n                return;\n            }\n            outRect.top = mDrawable.getIntrinsicHeight();\n            outRect.bottom = 0;\n        } else {\n            if (!needsVerticalDecoration()) {\n                return;\n            }\n            if (layoutManager.isLayoutRtl()) {\n                outRect.right = mDrawable.getIntrinsicWidth();\n                outRect.left = 0;\n            } else {\n                outRect.left = mDrawable.getIntrinsicWidth();\n                outRect.right = 0;\n            }\n        }\n\n    }\n\n    private void setOffsetAlongMainAxis(Rect outRect, int position,\n            FlexboxLayoutManager layoutManager, List<FlexLine> flexLines, int flexDirection) {\n        if (isFirstItemInLine(position, flexLines, layoutManager)) {\n            return;\n        }\n\n        if (layoutManager.isMainAxisDirectionHorizontal()) {\n            if (!needsVerticalDecoration()) {\n                outRect.left = 0;\n                outRect.right = 0;\n                return;\n            }\n            if (layoutManager.isLayoutRtl()) {\n                outRect.right = mDrawable.getIntrinsicWidth();\n                outRect.left = 0;\n            } else {\n                outRect.left = mDrawable.getIntrinsicWidth();\n                outRect.right = 0;\n            }\n        } else {\n            if (!needsHorizontalDecoration()) {\n                outRect.top = 0;\n                outRect.bottom = 0;\n                return;\n            }\n            if (flexDirection == FlexDirection.COLUMN_REVERSE) {\n                outRect.bottom = mDrawable.getIntrinsicHeight();\n                outRect.top = 0;\n            } else {\n                outRect.top = mDrawable.getIntrinsicHeight();\n                outRect.bottom = 0;\n            }\n        }\n\n    }\n\n    private void drawVerticalDecorations(Canvas canvas, RecyclerView parent) {\n        if (!needsVerticalDecoration()) {\n            return;\n        }\n        FlexboxLayoutManager layoutManager = (FlexboxLayoutManager) parent.getLayoutManager();\n        int parentTop = parent.getTop() - parent.getPaddingTop();\n        int parentBottom = parent.getBottom() + parent.getPaddingBottom();\n        int childCount = parent.getChildCount();\n        int flexDirection = layoutManager.getFlexDirection();\n        for (int i = 0; i < childCount; i++) {\n            View child = parent.getChildAt(i);\n\n            RecyclerView.LayoutParams lp = (RecyclerView.LayoutParams) child.getLayoutParams();\n\n            int left, right;\n            if (layoutManager.isLayoutRtl()) {\n                left = child.getRight() + lp.rightMargin;\n                right = left + mDrawable.getIntrinsicWidth();\n            } else {\n                right = child.getLeft() - lp.leftMargin;\n                left = right - mDrawable.getIntrinsicWidth();\n            }\n\n            int top, bottom;\n            if (layoutManager.isMainAxisDirectionHorizontal()) {\n                top = child.getTop() - lp.topMargin;\n                bottom = child.getBottom() + lp.bottomMargin;\n            } else {\n                if (flexDirection == FlexDirection.COLUMN_REVERSE) {\n                    bottom = child.getBottom() + lp.bottomMargin + mDrawable.getIntrinsicHeight();\n                    bottom = Math.min(bottom, parentBottom);\n                    top = child.getTop() - lp.topMargin;\n                } else {\n                    top = child.getTop() - lp.topMargin - mDrawable.getIntrinsicHeight();\n                    top = Math.max(top, parentTop);\n                    bottom = child.getBottom() + lp.bottomMargin;\n                }\n            }\n\n            mDrawable.setBounds(left, top, right, bottom);\n            mDrawable.draw(canvas);\n        }\n    }\n\n    private void drawHorizontalDecorations(Canvas canvas, RecyclerView parent) {\n        if (!needsHorizontalDecoration()) {\n            return;\n        }\n        FlexboxLayoutManager layoutManager = (FlexboxLayoutManager) parent.getLayoutManager();\n        int flexDirection = layoutManager.getFlexDirection();\n        int parentLeft = parent.getLeft() - parent.getPaddingLeft();\n        int parentRight = parent.getRight() + parent.getPaddingRight();\n        int childCount = parent.getChildCount();\n        for (int i = 0; i < childCount; i++) {\n            View child = parent.getChildAt(i);\n            RecyclerView.LayoutParams lp = (RecyclerView.LayoutParams) child.getLayoutParams();\n\n            int top, bottom;\n            if (flexDirection == FlexDirection.COLUMN_REVERSE) {\n                top = child.getBottom() + lp.bottomMargin;\n                bottom = top + mDrawable.getIntrinsicHeight();\n            } else {\n                bottom = child.getTop() - lp.topMargin;\n                top = bottom - mDrawable.getIntrinsicHeight();\n            }\n\n            int left, right;\n            if (layoutManager.isMainAxisDirectionHorizontal()) {\n                if (layoutManager.isLayoutRtl()) {\n                    right = child.getRight() + lp.rightMargin + mDrawable.getIntrinsicWidth();\n                    right = Math.min(right, parentRight);\n                    left = child.getLeft() - lp.leftMargin;\n                } else {\n                    left = child.getLeft() - lp.leftMargin - mDrawable.getIntrinsicWidth();\n                    left = Math.max(left, parentLeft);\n                    right = child.getRight() + lp.rightMargin;\n                }\n            } else {\n                left = child.getLeft() - lp.leftMargin;\n                right = child.getRight() + lp.rightMargin;\n            }\n            mDrawable.setBounds(left, top, right, bottom);\n            mDrawable.draw(canvas);\n        }\n    }\n\n    private boolean needsHorizontalDecoration() {\n        return (mOrientation & HORIZONTAL) > 0;\n    }\n\n    private boolean needsVerticalDecoration() {\n        return (mOrientation & VERTICAL) > 0;\n    }\n\n    /**\n     * @return {@code true} if the given position is the first item in a flex line.\n     */\n    private boolean isFirstItemInLine(int position, List<FlexLine> flexLines,\n            FlexboxLayoutManager layoutManager) {\n        int flexLineIndex = layoutManager.getPositionToFlexLineIndex(position);\n        if (flexLineIndex != NO_POSITION &&\n                flexLineIndex < layoutManager.getFlexLinesInternal().size() &&\n                layoutManager.getFlexLinesInternal().get(flexLineIndex).mFirstIndex == position) {\n            return true;\n        }\n        if (position == 0) {\n            return true;\n        }\n        if (flexLines.size() == 0) {\n            return false;\n        }\n        // Check if the position is the \"lastIndex + 1\" of the last line in case the FlexLine which\n        // has the View, whose index is position is not included in the flexLines. (E.g. flexLines\n        // is being calculated\n        FlexLine lastLine = flexLines.get(flexLines.size() - 1);\n        return lastLine.mLastIndex == position - 1;\n    }\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexboxLayout.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport android.content.Context;\nimport android.content.res.TypedArray;\nimport android.graphics.Canvas;\nimport android.graphics.drawable.Drawable;\nimport android.os.Parcel;\nimport android.os.Parcelable;\nimport android.util.AttributeSet;\nimport android.util.SparseIntArray;\nimport android.view.View;\nimport android.view.ViewGroup;\nimport android.widget.LinearLayout;\nimport android.widget.RelativeLayout;\n\nimport java.lang.annotation.Retention;\nimport java.lang.annotation.RetentionPolicy;\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport androidx.annotation.IntDef;\nimport androidx.annotation.Nullable;\nimport androidx.core.view.ViewCompat;\n\n/**\n * A layout that arranges its children in a way its attributes can be specified like the\n * CSS Flexible Box Layout Module.\n * This class extends the {@link ViewGroup} like other layout classes such as {@link LinearLayout}\n * or {@link RelativeLayout}, the attributes can be specified from a layout XML or from code.\n *\n * The supported attributes that you can use are:\n * <ul>\n * <li>{@code flexDirection}</li>\n * <li>{@code flexWrap}</li>\n * <li>{@code justifyContent}</li>\n * <li>{@code alignItems}</li>\n * <li>{@code alignContent}</li>\n * <li>{@code showDivider}</li>\n * <li>{@code showDividerHorizontal}</li>\n * <li>{@code showDividerVertical}</li>\n * <li>{@code dividerDrawable}</li>\n * <li>{@code dividerDrawableHorizontal}</li>\n * <li>{@code dividerDrawableVertical}</li>\n * <li>{@code maxLine}</li>\n * </ul>\n * for the FlexboxLayout.\n *\n * And for the children of the FlexboxLayout, you can use:\n * <ul>\n * <li>{@code layout_order}</li>\n * <li>{@code layout_flexGrow}</li>\n * <li>{@code layout_flexShrink}</li>\n * <li>{@code layout_flexBasisPercent}</li>\n * <li>{@code layout_alignSelf}</li>\n * <li>{@code layout_minWidth}</li>\n * <li>{@code layout_minHeight}</li>\n * <li>{@code layout_maxWidth}</li>\n * <li>{@code layout_maxHeight}</li>\n * <li>{@code layout_wrapBefore}</li>\n * </ul>\n */\npublic class FlexboxLayout extends ViewGroup implements FlexContainer {\n\n    /**\n     * The current value of the {@link FlexDirection}, the default value is {@link\n     * FlexDirection#ROW}.\n     *\n     * @see FlexDirection\n     */\n    private int mFlexDirection;\n\n    /**\n     * The current value of the {@link FlexWrap}, the default value is {@link FlexWrap#NOWRAP}.\n     *\n     * @see FlexWrap\n     */\n    private int mFlexWrap;\n\n    /**\n     * The current value of the {@link JustifyContent}, the default value is\n     * {@link JustifyContent#FLEX_START}.\n     *\n     * @see JustifyContent\n     */\n    private int mJustifyContent;\n\n    /**\n     * The current value of the {@link AlignItems}, the default value is\n     * {@link AlignItems#FLEX_START}.\n     *\n     * @see AlignItems\n     */\n    private int mAlignItems;\n\n    /**\n     * The current value of the {@link AlignContent}, the default value is\n     * {@link AlignContent#FLEX_START}.\n     *\n     * @see AlignContent\n     */\n    private int mAlignContent;\n\n    /**\n     * The current value of the maxLine attribute, which specifies the maximum number of flex lines.\n     */\n    private int mMaxLine = NOT_SET;\n\n    /**\n     * The int definition to be used as the arguments for the {@link #setShowDivider(int)},\n     * {@link #setShowDividerHorizontal(int)} or {@link #setShowDividerVertical(int)}.\n     * One or more of the values (such as\n     * {@link #SHOW_DIVIDER_BEGINNING} | {@link #SHOW_DIVIDER_MIDDLE}) can be passed to those set\n     * methods.\n     */\n    @IntDef(flag = true,\n            value = {\n                    SHOW_DIVIDER_NONE,\n                    SHOW_DIVIDER_BEGINNING,\n                    SHOW_DIVIDER_MIDDLE,\n                    SHOW_DIVIDER_END\n            })\n    @Retention(RetentionPolicy.SOURCE)\n    @SuppressWarnings(\"WeakerAccess\")\n    public @interface DividerMode {\n\n    }\n\n    /** Constant to show no dividers */\n    public static final int SHOW_DIVIDER_NONE = 0;\n\n    /** Constant to show a divider at the beginning of the flex lines (or flex items). */\n    public static final int SHOW_DIVIDER_BEGINNING = 1;\n\n    /** Constant to show dividers between flex lines or flex items. */\n    public static final int SHOW_DIVIDER_MIDDLE = 1 << 1;\n\n    /** Constant to show a divider at the end of the flex lines or flex items. */\n    public static final int SHOW_DIVIDER_END = 1 << 2;\n\n    /** The drawable to be drawn for the horizontal dividers. */\n    @Nullable\n    private Drawable mDividerDrawableHorizontal;\n\n    /** The drawable to be drawn for the vertical dividers. */\n    @Nullable\n    private Drawable mDividerDrawableVertical;\n\n    /**\n     * Indicates the divider mode for the {@link #mDividerDrawableHorizontal}. The value needs to\n     * be the combination of the value of {@link #SHOW_DIVIDER_NONE},\n     * {@link #SHOW_DIVIDER_BEGINNING}, {@link #SHOW_DIVIDER_MIDDLE} and {@link #SHOW_DIVIDER_END}\n     */\n    private int mShowDividerHorizontal;\n\n    /**\n     * Indicates the divider mode for the {@link #mDividerDrawableVertical}. The value needs to\n     * be the combination of the value of {@link #SHOW_DIVIDER_NONE},\n     * {@link #SHOW_DIVIDER_BEGINNING}, {@link #SHOW_DIVIDER_MIDDLE} and {@link #SHOW_DIVIDER_END}\n     */\n    private int mShowDividerVertical;\n\n    /** The height of the {@link #mDividerDrawableHorizontal}. */\n    private int mDividerHorizontalHeight;\n\n    /** The width of the {@link #mDividerDrawableVertical}. */\n    private int mDividerVerticalWidth;\n\n    /**\n     * Holds reordered indices, which {@link FlexItem#getOrder()} parameters are taken\n     * into account\n     */\n    private int[] mReorderedIndices;\n\n    /**\n     * Caches the {@link FlexItem#getOrder()} attributes for children views.\n     * Key: the index of the view reordered indices using the {@link FlexItem#getOrder()}\n     * isn't taken into account)\n     * Value: the value for the order attribute\n     */\n    private SparseIntArray mOrderCache;\n\n    private FlexboxHelper mFlexboxHelper = new FlexboxHelper(this);\n\n    private List<FlexLine> mFlexLines = new ArrayList<>();\n\n    /**\n     * Used for receiving the calculation of the flex results to avoid creating a new instance\n     * every time flex lines are calculated.\n     */\n    private FlexboxHelper.FlexLinesResult mFlexLinesResult = new FlexboxHelper.FlexLinesResult();\n\n    public FlexboxLayout(Context context) {\n        this(context, null);\n    }\n\n    public FlexboxLayout(Context context, AttributeSet attrs) {\n        this(context, attrs, 0);\n    }\n\n    public FlexboxLayout(Context context, AttributeSet attrs, int defStyleAttr) {\n        super(context, attrs, defStyleAttr);\n\n        TypedArray a = context.obtainStyledAttributes(\n                attrs, R.styleable.FlexboxLayout, defStyleAttr, 0);\n        mFlexDirection = a\n                .getInt(R.styleable.FlexboxLayout_flexDirection, FlexDirection.ROW);\n        mFlexWrap = a.getInt(R.styleable.FlexboxLayout_flexWrap, FlexWrap.NOWRAP);\n        mJustifyContent = a\n                .getInt(R.styleable.FlexboxLayout_justifyContent, JustifyContent.FLEX_START);\n        mAlignItems = a.getInt(R.styleable.FlexboxLayout_alignItems, AlignItems.FLEX_START);\n        mAlignContent = a.getInt(R.styleable.FlexboxLayout_alignContent, AlignContent.FLEX_START);\n        mMaxLine = a.getInt(R.styleable.FlexboxLayout_maxLine, NOT_SET);\n        Drawable drawable = a.getDrawable(R.styleable.FlexboxLayout_dividerDrawable);\n        if (drawable != null) {\n            setDividerDrawableHorizontal(drawable);\n            setDividerDrawableVertical(drawable);\n        }\n        Drawable drawableHorizontal = a\n                .getDrawable(R.styleable.FlexboxLayout_dividerDrawableHorizontal);\n        if (drawableHorizontal != null) {\n            setDividerDrawableHorizontal(drawableHorizontal);\n        }\n        Drawable drawableVertical = a\n                .getDrawable(R.styleable.FlexboxLayout_dividerDrawableVertical);\n        if (drawableVertical != null) {\n            setDividerDrawableVertical(drawableVertical);\n        }\n        int dividerMode = a.getInt(R.styleable.FlexboxLayout_showDivider, SHOW_DIVIDER_NONE);\n        if (dividerMode != SHOW_DIVIDER_NONE) {\n            mShowDividerVertical = dividerMode;\n            mShowDividerHorizontal = dividerMode;\n        }\n        int dividerModeVertical = a\n                .getInt(R.styleable.FlexboxLayout_showDividerVertical, SHOW_DIVIDER_NONE);\n        if (dividerModeVertical != SHOW_DIVIDER_NONE) {\n            mShowDividerVertical = dividerModeVertical;\n        }\n        int dividerModeHorizontal = a\n                .getInt(R.styleable.FlexboxLayout_showDividerHorizontal, SHOW_DIVIDER_NONE);\n        if (dividerModeHorizontal != SHOW_DIVIDER_NONE) {\n            mShowDividerHorizontal = dividerModeHorizontal;\n        }\n        a.recycle();\n    }\n\n    @Override\n    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {\n        if (mOrderCache == null) {\n            mOrderCache = new SparseIntArray(getChildCount());\n        }\n        if (mFlexboxHelper.isOrderChangedFromLastMeasurement(mOrderCache)) {\n            mReorderedIndices = mFlexboxHelper.createReorderedIndices(mOrderCache);\n        }\n\n        // TODO: Only calculate the children views which are affected from the last measure.\n\n        switch (mFlexDirection) {\n            case FlexDirection.ROW: // Intentional fall through\n            case FlexDirection.ROW_REVERSE:\n                measureHorizontal(widthMeasureSpec, heightMeasureSpec);\n                break;\n            case FlexDirection.COLUMN: // Intentional fall through\n            case FlexDirection.COLUMN_REVERSE:\n                measureVertical(widthMeasureSpec, heightMeasureSpec);\n                break;\n            default:\n                throw new IllegalStateException(\n                        \"Invalid value for the flex direction is set: \" + mFlexDirection);\n        }\n    }\n\n    @Override\n    public int getFlexItemCount() {\n        return getChildCount();\n    }\n\n    @Override\n    public View getFlexItemAt(int index) {\n        return getChildAt(index);\n    }\n\n    /**\n     * Returns a View, which is reordered by taking {@link LayoutParams#mOrder} parameters\n     * into account.\n     *\n     * @param index the index of the view\n     * @return the reordered view, which {@link LayoutParams@order} is taken into account.\n     * If the index is negative or out of bounds of the number of contained views,\n     * returns {@code null}.\n     */\n    public View getReorderedChildAt(int index) {\n        if (index < 0 || index >= mReorderedIndices.length) {\n            return null;\n        }\n        return getChildAt(mReorderedIndices[index]);\n    }\n\n    @Override\n    public View getReorderedFlexItemAt(int index) {\n        return getReorderedChildAt(index);\n    }\n\n    @Override\n    public void addView(View child, int index, ViewGroup.LayoutParams params) {\n        if (mOrderCache == null) {\n            mOrderCache = new SparseIntArray(getChildCount());\n        }\n        // Create an array for the reordered indices before the View is added in the parent\n        // ViewGroup since otherwise reordered indices won't be in effect before the\n        // FlexboxLayout's onMeasure is called.\n        // Because requestLayout is requested in the super.addView method.\n        mReorderedIndices = mFlexboxHelper\n                .createReorderedIndices(child, index, params, mOrderCache);\n        super.addView(child, index, params);\n    }\n\n    /**\n     * Sub method for {@link #onMeasure(int, int)}, when the main axis direction is horizontal\n     * (either left to right or right to left).\n     *\n     * @param widthMeasureSpec  horizontal space requirements as imposed by the parent\n     * @param heightMeasureSpec vertical space requirements as imposed by the parent\n     * @see #onMeasure(int, int)\n     * @see #setFlexDirection(int)\n     * @see #setFlexWrap(int)\n     * @see #setAlignItems(int)\n     * @see #setAlignContent(int)\n     */\n    private void measureHorizontal(int widthMeasureSpec, int heightMeasureSpec) {\n        mFlexLines.clear();\n\n        mFlexLinesResult.reset();\n        mFlexboxHelper\n                .calculateHorizontalFlexLines(mFlexLinesResult, widthMeasureSpec,\n                        heightMeasureSpec);\n        mFlexLines = mFlexLinesResult.mFlexLines;\n\n        mFlexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec);\n\n        // TODO: Consider the case any individual child's mAlignSelf is set to ALIGN_SELF_BASELINE\n        if (mAlignItems == AlignItems.BASELINE) {\n            for (FlexLine flexLine : mFlexLines) {\n                // The largest height value that also take the baseline shift into account\n                int largestHeightInLine = Integer.MIN_VALUE;\n                for (int i = 0; i < flexLine.mItemCount; i++) {\n                    int viewIndex = flexLine.mFirstIndex + i;\n                    View child = getReorderedChildAt(viewIndex);\n                    if (child == null || child.getVisibility() == View.GONE) {\n                        continue;\n                    }\n                    LayoutParams lp = (LayoutParams) child.getLayoutParams();\n                    if (mFlexWrap != FlexWrap.WRAP_REVERSE) {\n                        int marginTop = flexLine.mMaxBaseline - child.getBaseline();\n                        marginTop = Math.max(marginTop, lp.topMargin);\n                        largestHeightInLine = Math.max(largestHeightInLine,\n                                child.getMeasuredHeight() + marginTop + lp.bottomMargin);\n                    } else {\n                        int marginBottom = flexLine.mMaxBaseline - child.getMeasuredHeight() +\n                                child.getBaseline();\n                        marginBottom = Math.max(marginBottom, lp.bottomMargin);\n                        largestHeightInLine = Math.max(largestHeightInLine,\n                                child.getMeasuredHeight() + lp.topMargin + marginBottom);\n                    }\n                }\n                flexLine.mCrossSize = largestHeightInLine;\n            }\n        }\n\n        mFlexboxHelper.determineCrossSize(widthMeasureSpec, heightMeasureSpec,\n                getPaddingTop() + getPaddingBottom());\n        // Now cross size for each flex line is determined.\n        // Expand the views if alignItems (or mAlignSelf in each child view) is set to stretch\n        mFlexboxHelper.stretchViews();\n        setMeasuredDimensionForFlex(mFlexDirection, widthMeasureSpec, heightMeasureSpec,\n                mFlexLinesResult.mChildState);\n    }\n\n    /**\n     * Sub method for {@link #onMeasure(int, int)} when the main axis direction is vertical\n     * (either from top to bottom or bottom to top).\n     *\n     * @param widthMeasureSpec  horizontal space requirements as imposed by the parent\n     * @param heightMeasureSpec vertical space requirements as imposed by the parent\n     * @see #onMeasure(int, int)\n     * @see #setFlexDirection(int)\n     * @see #setFlexWrap(int)\n     * @see #setAlignItems(int)\n     * @see #setAlignContent(int)\n     */\n    private void measureVertical(int widthMeasureSpec, int heightMeasureSpec) {\n        mFlexLines.clear();\n        mFlexLinesResult.reset();\n        mFlexboxHelper.calculateVerticalFlexLines(mFlexLinesResult, widthMeasureSpec,\n                heightMeasureSpec);\n        mFlexLines = mFlexLinesResult.mFlexLines;\n\n        mFlexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec);\n        mFlexboxHelper.determineCrossSize(widthMeasureSpec, heightMeasureSpec,\n                getPaddingLeft() + getPaddingRight());\n        // Now cross size for each flex line is determined.\n        // Expand the views if alignItems (or mAlignSelf in each child view) is set to stretch\n        mFlexboxHelper.stretchViews();\n        setMeasuredDimensionForFlex(mFlexDirection, widthMeasureSpec, heightMeasureSpec,\n                mFlexLinesResult.mChildState);\n    }\n\n    /**\n     * Set this FlexboxLayouts' width and height depending on the calculated size of main axis and\n     * cross axis.\n     *\n     * @param flexDirection     the value of the flex direction\n     * @param widthMeasureSpec  horizontal space requirements as imposed by the parent\n     * @param heightMeasureSpec vertical space requirements as imposed by the parent\n     * @param childState        the child state of the View\n     * @see #getFlexDirection()\n     * @see #setFlexDirection(int)\n     */\n    private void setMeasuredDimensionForFlex(@FlexDirection int flexDirection, int widthMeasureSpec,\n            int heightMeasureSpec, int childState) {\n        int widthMode = MeasureSpec.getMode(widthMeasureSpec);\n        int widthSize = MeasureSpec.getSize(widthMeasureSpec);\n        int heightMode = MeasureSpec.getMode(heightMeasureSpec);\n        int heightSize = MeasureSpec.getSize(heightMeasureSpec);\n        int calculatedMaxHeight;\n        int calculatedMaxWidth;\n        switch (flexDirection) {\n            case FlexDirection.ROW: // Intentional fall through\n            case FlexDirection.ROW_REVERSE:\n                calculatedMaxHeight = getSumOfCrossSize() + getPaddingTop()\n                        + getPaddingBottom();\n                calculatedMaxWidth = getLargestMainSize();\n                break;\n            case FlexDirection.COLUMN: // Intentional fall through\n            case FlexDirection.COLUMN_REVERSE:\n                calculatedMaxHeight = getLargestMainSize();\n                calculatedMaxWidth = getSumOfCrossSize() + getPaddingLeft() + getPaddingRight();\n                break;\n            default:\n                throw new IllegalArgumentException(\"Invalid flex direction: \" + flexDirection);\n        }\n\n        int widthSizeAndState;\n        switch (widthMode) {\n            case MeasureSpec.EXACTLY:\n                if (widthSize < calculatedMaxWidth) {\n                    childState = View\n                            .combineMeasuredStates(childState, View.MEASURED_STATE_TOO_SMALL);\n                }\n                widthSizeAndState = View.resolveSizeAndState(widthSize, widthMeasureSpec,\n                        childState);\n                break;\n            case MeasureSpec.AT_MOST: {\n                if (widthSize < calculatedMaxWidth) {\n                    childState = View\n                            .combineMeasuredStates(childState, View.MEASURED_STATE_TOO_SMALL);\n                } else {\n                    widthSize = calculatedMaxWidth;\n                }\n                widthSizeAndState = View.resolveSizeAndState(widthSize, widthMeasureSpec,\n                        childState);\n                break;\n            }\n            case MeasureSpec.UNSPECIFIED: {\n                widthSizeAndState = View\n                        .resolveSizeAndState(calculatedMaxWidth, widthMeasureSpec, childState);\n                break;\n            }\n            default:\n                throw new IllegalStateException(\"Unknown width mode is set: \" + widthMode);\n        }\n        int heightSizeAndState;\n        switch (heightMode) {\n            case MeasureSpec.EXACTLY:\n                if (heightSize < calculatedMaxHeight) {\n                    childState = View.combineMeasuredStates(childState,\n                            View.MEASURED_STATE_TOO_SMALL\n                                    >> View.MEASURED_HEIGHT_STATE_SHIFT);\n                }\n                heightSizeAndState = View.resolveSizeAndState(heightSize, heightMeasureSpec,\n                        childState);\n                break;\n            case MeasureSpec.AT_MOST: {\n                if (heightSize < calculatedMaxHeight) {\n                    childState = View.combineMeasuredStates(childState,\n                            View.MEASURED_STATE_TOO_SMALL\n                                    >> View.MEASURED_HEIGHT_STATE_SHIFT);\n                } else {\n                    heightSize = calculatedMaxHeight;\n                }\n                heightSizeAndState = View.resolveSizeAndState(heightSize, heightMeasureSpec,\n                        childState);\n                break;\n            }\n            case MeasureSpec.UNSPECIFIED: {\n                heightSizeAndState = View.resolveSizeAndState(calculatedMaxHeight,\n                        heightMeasureSpec, childState);\n                break;\n            }\n            default:\n                throw new IllegalStateException(\"Unknown height mode is set: \" + heightMode);\n        }\n        setMeasuredDimension(widthSizeAndState, heightSizeAndState);\n    }\n\n    @Override\n    public int getLargestMainSize() {\n        int largestSize = Integer.MIN_VALUE;\n        for (FlexLine flexLine : mFlexLines) {\n            largestSize = Math.max(largestSize, flexLine.mMainSize);\n        }\n        return largestSize;\n    }\n\n    @Override\n    public int getSumOfCrossSize() {\n        int sum = 0;\n        for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n            FlexLine flexLine = mFlexLines.get(i);\n\n            // Judge if the beginning or middle dividers are required\n            if (hasDividerBeforeFlexLine(i)) {\n                if (isMainAxisDirectionHorizontal()) {\n                    sum += mDividerHorizontalHeight;\n                } else {\n                    sum += mDividerVerticalWidth;\n                }\n            }\n\n            // Judge if the end divider is required\n            if (hasEndDividerAfterFlexLine(i)) {\n                if (isMainAxisDirectionHorizontal()) {\n                    sum += mDividerHorizontalHeight;\n                } else {\n                    sum += mDividerVerticalWidth;\n                }\n            }\n            sum += flexLine.mCrossSize;\n        }\n        return sum;\n    }\n\n    @Override\n    public boolean isMainAxisDirectionHorizontal() {\n        return mFlexDirection == FlexDirection.ROW || mFlexDirection == FlexDirection.ROW_REVERSE;\n    }\n\n    @Override\n    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {\n        int layoutDirection = ViewCompat.getLayoutDirection(this);\n        boolean isRtl;\n        switch (mFlexDirection) {\n            case FlexDirection.ROW:\n                isRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                layoutHorizontal(isRtl, left, top, right, bottom);\n                break;\n            case FlexDirection.ROW_REVERSE:\n                isRtl = layoutDirection != ViewCompat.LAYOUT_DIRECTION_RTL;\n                layoutHorizontal(isRtl, left, top, right, bottom);\n                break;\n            case FlexDirection.COLUMN:\n                isRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    isRtl = !isRtl;\n                }\n                layoutVertical(isRtl, false, left, top, right, bottom);\n                break;\n            case FlexDirection.COLUMN_REVERSE:\n                isRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    isRtl = !isRtl;\n                }\n                layoutVertical(isRtl, true, left, top, right, bottom);\n                break;\n            default:\n                throw new IllegalStateException(\"Invalid flex direction is set: \" + mFlexDirection);\n        }\n    }\n\n    /**\n     * Sub method for {@link #onLayout(boolean, int, int, int, int)} when the\n     * {@link #mFlexDirection} is either {@link FlexDirection#ROW} or\n     * {@link FlexDirection#ROW_REVERSE}.\n     *\n     * @param isRtl  {@code true} if the horizontal layout direction is right to left, {@code\n     *               false} otherwise.\n     * @param left   the left position of this View\n     * @param top    the top position of this View\n     * @param right  the right position of this View\n     * @param bottom the bottom position of this View\n     * @see #getFlexWrap()\n     * @see #setFlexWrap(int)\n     * @see #getJustifyContent()\n     * @see #setJustifyContent(int)\n     * @see #getAlignItems()\n     * @see #setAlignItems(int)\n     * @see LayoutParams#mAlignSelf\n     */\n    private void layoutHorizontal(boolean isRtl, int left, int top, int right, int bottom) {\n        int paddingLeft = getPaddingLeft();\n        int paddingRight = getPaddingRight();\n        // Use float to reduce the round error that may happen in when justifyContent ==\n        // SPACE_BETWEEN or SPACE_AROUND\n        float childLeft;\n\n        int height = bottom - top;\n        int width = right - left;\n        // childBottom is used if the mFlexWrap is WRAP_REVERSE otherwise\n        // childTop is used to align the vertical position of the children views.\n        int childBottom = height - getPaddingBottom();\n        int childTop = getPaddingTop();\n\n        // Used only for RTL layout\n        // Use float to reduce the round error that may happen in when justifyContent ==\n        // SPACE_BETWEEN or SPACE_AROUND\n        float childRight;\n        for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n            FlexLine flexLine = mFlexLines.get(i);\n            if (hasDividerBeforeFlexLine(i)) {\n                childBottom -= mDividerHorizontalHeight;\n                childTop += mDividerHorizontalHeight;\n            }\n            float spaceBetweenItem = 0f;\n            switch (mJustifyContent) {\n                case JustifyContent.FLEX_START:\n                    childLeft = paddingLeft;\n                    childRight = width - paddingRight;\n                    break;\n                case JustifyContent.FLEX_END:\n                    childLeft = width - flexLine.mMainSize + paddingRight;\n                    childRight = flexLine.mMainSize - paddingLeft;\n                    break;\n                case JustifyContent.CENTER:\n                    childLeft = paddingLeft + (width - flexLine.mMainSize) / 2f;\n                    childRight = width - paddingRight - (width - flexLine.mMainSize) / 2f;\n                    break;\n                case JustifyContent.SPACE_AROUND: {\n                    int visibleCount = flexLine.getItemCountNotGone();\n                    if (visibleCount != 0) {\n                        spaceBetweenItem = (width - flexLine.mMainSize)\n                                / (float) visibleCount;\n                    }\n                    childLeft = paddingLeft + spaceBetweenItem / 2f;\n                    childRight = width - paddingRight - spaceBetweenItem / 2f;\n                    break;\n                }\n                case JustifyContent.SPACE_BETWEEN: {\n                    childLeft = paddingLeft;\n                    int visibleCount = flexLine.getItemCountNotGone();\n                    float denominator = visibleCount != 1 ? visibleCount - 1 : 1f;\n                    spaceBetweenItem = (width - flexLine.mMainSize) / denominator;\n                    childRight = width - paddingRight;\n                    break;\n                }\n                case JustifyContent.SPACE_EVENLY: {\n                    int visibleCount = flexLine.getItemCountNotGone();\n                    if (visibleCount != 0) {\n                        spaceBetweenItem = (width - flexLine.mMainSize)\n                                / (float) (visibleCount + 1);\n                    }\n                    childLeft = paddingLeft + spaceBetweenItem;\n                    childRight = width - paddingRight - spaceBetweenItem;\n                    break;\n                }\n                default:\n                    throw new IllegalStateException(\n                            \"Invalid justifyContent is set: \" + mJustifyContent);\n            }\n            spaceBetweenItem = Math.max(spaceBetweenItem, 0);\n\n            for (int j = 0; j < flexLine.mItemCount; j++) {\n                int index = flexLine.mFirstIndex + j;\n                View child = getReorderedChildAt(index);\n                if (child == null || child.getVisibility() == View.GONE) {\n                    continue;\n                }\n                LayoutParams lp = ((LayoutParams) child.getLayoutParams());\n                childLeft += lp.leftMargin;\n                childRight -= lp.rightMargin;\n                int beforeDividerLength = 0;\n                int endDividerLength = 0;\n                if (hasDividerBeforeChildAtAlongMainAxis(index, j)) {\n                    beforeDividerLength = mDividerVerticalWidth;\n                    childLeft += beforeDividerLength;\n                    childRight -= beforeDividerLength;\n                }\n                if (j == flexLine.mItemCount - 1 && (mShowDividerVertical & SHOW_DIVIDER_END) > 0) {\n                    endDividerLength = mDividerVerticalWidth;\n                }\n\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    if (isRtl) {\n                        mFlexboxHelper.layoutSingleChildHorizontal(child, flexLine,\n                                Math.round(childRight) - child.getMeasuredWidth(),\n                                childBottom - child.getMeasuredHeight(), Math.round(childRight),\n                                childBottom);\n                    } else {\n                        mFlexboxHelper.layoutSingleChildHorizontal(child, flexLine,\n                                Math.round(childLeft), childBottom - child.getMeasuredHeight(),\n                                Math.round(childLeft) + child.getMeasuredWidth(), childBottom);\n                    }\n                } else {\n                    if (isRtl) {\n                        mFlexboxHelper.layoutSingleChildHorizontal(child, flexLine,\n                                Math.round(childRight) - child.getMeasuredWidth(),\n                                childTop, Math.round(childRight),\n                                childTop + child.getMeasuredHeight());\n                    } else {\n                        mFlexboxHelper.layoutSingleChildHorizontal(child, flexLine,\n                                Math.round(childLeft), childTop,\n                                Math.round(childLeft) + child.getMeasuredWidth(),\n                                childTop + child.getMeasuredHeight());\n                    }\n                }\n                childLeft += child.getMeasuredWidth() + spaceBetweenItem + lp.rightMargin;\n                childRight -= child.getMeasuredWidth() + spaceBetweenItem + lp.leftMargin;\n\n                if (isRtl) {\n                    flexLine.updatePositionFromView(child, /*leftDecoration*/endDividerLength, 0,\n                            /*rightDecoration*/ beforeDividerLength, 0);\n                } else {\n                    flexLine.updatePositionFromView(child, /*leftDecoration*/beforeDividerLength, 0,\n                            /*rightDecoration*/ endDividerLength, 0);\n                }\n            }\n            childTop += flexLine.mCrossSize;\n            childBottom -= flexLine.mCrossSize;\n        }\n    }\n\n    /**\n     * Sub method for {@link #onLayout(boolean, int, int, int, int)} when the\n     * {@link #mFlexDirection} is either {@link FlexDirection#COLUMN} or\n     * {@link FlexDirection#COLUMN_REVERSE}.\n     *\n     * @param isRtl           {@code true} if the horizontal layout direction is right to left,\n     *                        {@code false}\n     *                        otherwise\n     * @param fromBottomToTop {@code true} if the layout direction is bottom to top, {@code false}\n     *                        otherwise\n     * @param left            the left position of this View\n     * @param top             the top position of this View\n     * @param right           the right position of this View\n     * @param bottom          the bottom position of this View\n     * @see #getFlexWrap()\n     * @see #setFlexWrap(int)\n     * @see #getJustifyContent()\n     * @see #setJustifyContent(int)\n     * @see #getAlignItems()\n     * @see #setAlignItems(int)\n     * @see LayoutParams#mAlignSelf\n     */\n    private void layoutVertical(boolean isRtl, boolean fromBottomToTop, int left, int top,\n            int right, int bottom) {\n        int paddingTop = getPaddingTop();\n        int paddingBottom = getPaddingBottom();\n\n        int paddingRight = getPaddingRight();\n        int childLeft = getPaddingLeft();\n\n        int width = right - left;\n        int height = bottom - top;\n        // childRight is used if the mFlexWrap is WRAP_REVERSE otherwise\n        // childLeft is used to align the horizontal position of the children views.\n        int childRight = width - paddingRight;\n\n        // Use float to reduce the round error that may happen in when justifyContent ==\n        // SPACE_BETWEEN or SPACE_AROUND\n        float childTop;\n\n        // Used only for if the direction is from bottom to top\n        float childBottom;\n\n        for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n            FlexLine flexLine = mFlexLines.get(i);\n            if (hasDividerBeforeFlexLine(i)) {\n                childLeft += mDividerVerticalWidth;\n                childRight -= mDividerVerticalWidth;\n            }\n            float spaceBetweenItem = 0f;\n            switch (mJustifyContent) {\n                case JustifyContent.FLEX_START:\n                    childTop = paddingTop;\n                    childBottom = height - paddingBottom;\n                    break;\n                case JustifyContent.FLEX_END:\n                    childTop = height - flexLine.mMainSize + paddingBottom;\n                    childBottom = flexLine.mMainSize - paddingTop;\n                    break;\n                case JustifyContent.CENTER:\n                    childTop = paddingTop + (height - flexLine.mMainSize) / 2f;\n                    childBottom = height - paddingBottom - (height - flexLine.mMainSize) / 2f;\n                    break;\n                case JustifyContent.SPACE_AROUND: {\n                    int visibleCount = flexLine.getItemCountNotGone();\n                    if (visibleCount != 0) {\n                        spaceBetweenItem = (height - flexLine.mMainSize)\n                                / (float) visibleCount;\n                    }\n                    childTop = paddingTop + spaceBetweenItem / 2f;\n                    childBottom = height - paddingBottom - spaceBetweenItem / 2f;\n                    break;\n                }\n                case JustifyContent.SPACE_BETWEEN: {\n                    childTop = paddingTop;\n                    int visibleCount = flexLine.getItemCountNotGone();\n                    float denominator = visibleCount != 1 ? visibleCount - 1 : 1f;\n                    spaceBetweenItem = (height - flexLine.mMainSize) / denominator;\n                    childBottom = height - paddingBottom;\n                    break;\n                }\n                case JustifyContent.SPACE_EVENLY: {\n                    int visibleCount = flexLine.getItemCountNotGone();\n                    if (visibleCount != 0) {\n                        spaceBetweenItem = (height - flexLine.mMainSize)\n                                / (float) (visibleCount + 1);\n                    }\n                    childTop = paddingTop + spaceBetweenItem;\n                    childBottom = height - paddingBottom - spaceBetweenItem;\n                    break;\n                }\n                default:\n                    throw new IllegalStateException(\n                            \"Invalid justifyContent is set: \" + mJustifyContent);\n            }\n            spaceBetweenItem = Math.max(spaceBetweenItem, 0);\n\n            for (int j = 0; j < flexLine.mItemCount; j++) {\n                int index = flexLine.mFirstIndex + j;\n                View child = getReorderedChildAt(index);\n                if (child == null || child.getVisibility() == View.GONE) {\n                    continue;\n                }\n                LayoutParams lp = ((LayoutParams) child.getLayoutParams());\n                childTop += lp.topMargin;\n                childBottom -= lp.bottomMargin;\n                int beforeDividerLength = 0;\n                int endDividerLength = 0;\n                if (hasDividerBeforeChildAtAlongMainAxis(index, j)) {\n                    beforeDividerLength = mDividerHorizontalHeight;\n                    childTop += beforeDividerLength;\n                    childBottom -= beforeDividerLength;\n                }\n                if (j == flexLine.mItemCount - 1\n                        && (mShowDividerHorizontal & SHOW_DIVIDER_END) > 0) {\n                    endDividerLength = mDividerHorizontalHeight;\n                }\n                if (isRtl) {\n                    if (fromBottomToTop) {\n                        mFlexboxHelper.layoutSingleChildVertical(child, flexLine, true,\n                                childRight - child.getMeasuredWidth(),\n                                Math.round(childBottom) - child.getMeasuredHeight(), childRight,\n                                Math.round(childBottom));\n                    } else {\n                        mFlexboxHelper.layoutSingleChildVertical(child, flexLine, true,\n                                childRight - child.getMeasuredWidth(), Math.round(childTop),\n                                childRight, Math.round(childTop) + child.getMeasuredHeight());\n                    }\n                } else {\n                    if (fromBottomToTop) {\n                        mFlexboxHelper.layoutSingleChildVertical(child, flexLine, false,\n                                childLeft, Math.round(childBottom) - child.getMeasuredHeight(),\n                                childLeft + child.getMeasuredWidth(), Math.round(childBottom));\n                    } else {\n                        mFlexboxHelper.layoutSingleChildVertical(child, flexLine, false,\n                                childLeft, Math.round(childTop),\n                                childLeft + child.getMeasuredWidth(),\n                                Math.round(childTop) + child.getMeasuredHeight());\n                    }\n                }\n                childTop += child.getMeasuredHeight() + spaceBetweenItem + lp.bottomMargin;\n                childBottom -= child.getMeasuredHeight() + spaceBetweenItem + lp.topMargin;\n\n                if (fromBottomToTop) {\n                    flexLine.updatePositionFromView(child, 0, /*topDecoration*/endDividerLength, 0,\n                            /*bottomDecoration*/ beforeDividerLength);\n                } else {\n                    flexLine.updatePositionFromView(child, 0, /*topDecoration*/beforeDividerLength,\n                            0, /*bottomDecoration*/endDividerLength);\n                }\n            }\n            childLeft += flexLine.mCrossSize;\n            childRight -= flexLine.mCrossSize;\n        }\n    }\n\n\n    @Override\n    protected void onDraw(Canvas canvas) {\n        if (mDividerDrawableVertical == null && mDividerDrawableHorizontal == null) {\n            return;\n        }\n        if (mShowDividerHorizontal == SHOW_DIVIDER_NONE\n                && mShowDividerVertical == SHOW_DIVIDER_NONE) {\n            return;\n        }\n\n        int layoutDirection = ViewCompat.getLayoutDirection(this);\n        boolean isRtl;\n        boolean fromBottomToTop = false;\n        switch (mFlexDirection) {\n            case FlexDirection.ROW:\n                isRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    fromBottomToTop = true;\n                }\n                drawDividersHorizontal(canvas, isRtl, fromBottomToTop);\n                break;\n            case FlexDirection.ROW_REVERSE:\n                isRtl = layoutDirection != ViewCompat.LAYOUT_DIRECTION_RTL;\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    fromBottomToTop = true;\n                }\n                drawDividersHorizontal(canvas, isRtl, fromBottomToTop);\n                break;\n            case FlexDirection.COLUMN:\n                isRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    isRtl = !isRtl;\n                }\n                drawDividersVertical(canvas, isRtl, false);\n                break;\n            case FlexDirection.COLUMN_REVERSE:\n                isRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    isRtl = !isRtl;\n                }\n                drawDividersVertical(canvas, isRtl, true);\n                break;\n        }\n    }\n\n    /**\n     * Sub method for {@link #onDraw(Canvas)} when the main axis direction is horizontal\n     * ({@link #mFlexDirection} is either of {@link FlexDirection#ROW} or\n     * {@link FlexDirection#ROW_REVERSE}.\n     *\n     * @param canvas          the canvas on which the background will be drawn\n     * @param isRtl           {@code true} when the horizontal layout direction is right to left,\n     *                        {@code false} otherwise\n     * @param fromBottomToTop {@code true} when the vertical layout direction is bottom to top,\n     *                        {@code false} otherwise\n     */\n    private void drawDividersHorizontal(Canvas canvas, boolean isRtl, boolean fromBottomToTop) {\n        int paddingLeft = getPaddingLeft();\n        int paddingRight = getPaddingRight();\n        int horizontalDividerLength = Math.max(0, getWidth() - paddingRight - paddingLeft);\n        for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n            FlexLine flexLine = mFlexLines.get(i);\n            for (int j = 0; j < flexLine.mItemCount; j++) {\n                int viewIndex = flexLine.mFirstIndex + j;\n                View view = getReorderedChildAt(viewIndex);\n                if (view == null || view.getVisibility() == View.GONE) {\n                    continue;\n                }\n                LayoutParams lp = (LayoutParams) view.getLayoutParams();\n\n                // Judge if the beginning or middle divider is needed\n                if (hasDividerBeforeChildAtAlongMainAxis(viewIndex, j)) {\n                    int dividerLeft;\n                    if (isRtl) {\n                        dividerLeft = view.getRight() + lp.rightMargin;\n                    } else {\n                        dividerLeft = view.getLeft() - lp.leftMargin - mDividerVerticalWidth;\n                    }\n\n                    drawVerticalDivider(canvas, dividerLeft, flexLine.mTop, flexLine.mCrossSize);\n                }\n\n                // Judge if the end divider is needed\n                if (j == flexLine.mItemCount - 1) {\n                    if ((mShowDividerVertical & SHOW_DIVIDER_END) > 0) {\n                        int dividerLeft;\n                        if (isRtl) {\n                            dividerLeft = view.getLeft() - lp.leftMargin - mDividerVerticalWidth;\n                        } else {\n                            dividerLeft = view.getRight() + lp.rightMargin;\n                        }\n\n                        drawVerticalDivider(canvas, dividerLeft, flexLine.mTop,\n                                flexLine.mCrossSize);\n                    }\n                }\n            }\n\n            // Judge if the beginning or middle dividers are needed before the flex line\n            if (hasDividerBeforeFlexLine(i)) {\n                int horizontalDividerTop;\n                if (fromBottomToTop) {\n                    horizontalDividerTop = flexLine.mBottom;\n                } else {\n                    horizontalDividerTop = flexLine.mTop - mDividerHorizontalHeight;\n                }\n                drawHorizontalDivider(canvas, paddingLeft, horizontalDividerTop,\n                        horizontalDividerLength);\n            }\n            // Judge if the end divider is needed before the flex line\n            if (hasEndDividerAfterFlexLine(i)) {\n                if ((mShowDividerHorizontal & SHOW_DIVIDER_END) > 0) {\n                    int horizontalDividerTop;\n                    if (fromBottomToTop) {\n                        horizontalDividerTop = flexLine.mTop - mDividerHorizontalHeight;\n                    } else {\n                        horizontalDividerTop = flexLine.mBottom;\n                    }\n                    drawHorizontalDivider(canvas, paddingLeft, horizontalDividerTop,\n                            horizontalDividerLength);\n                }\n            }\n        }\n    }\n\n    /**\n     * Sub method for {@link #onDraw(Canvas)} when the main axis direction is vertical\n     * ({@link #mFlexDirection} is either of {@link FlexDirection#COLUMN} or\n     * {@link FlexDirection#COLUMN_REVERSE}.\n     *\n     * @param canvas          the canvas on which the background will be drawn\n     * @param isRtl           {@code true} when the horizontal layout direction is right to left,\n     *                        {@code false} otherwise\n     * @param fromBottomToTop {@code true} when the vertical layout direction is bottom to top,\n     *                        {@code false} otherwise\n     */\n    private void drawDividersVertical(Canvas canvas, boolean isRtl, boolean fromBottomToTop) {\n        int paddingTop = getPaddingTop();\n        int paddingBottom = getPaddingBottom();\n        int verticalDividerLength = Math.max(0, getHeight() - paddingBottom - paddingTop);\n        for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n            FlexLine flexLine = mFlexLines.get(i);\n\n            // Draw horizontal dividers if needed\n            for (int j = 0; j < flexLine.mItemCount; j++) {\n                int viewIndex = flexLine.mFirstIndex + j;\n                View view = getReorderedChildAt(viewIndex);\n                if (view == null || view.getVisibility() == View.GONE) {\n                    continue;\n                }\n                LayoutParams lp = (LayoutParams) view.getLayoutParams();\n\n                // Judge if the beginning or middle divider is needed\n                if (hasDividerBeforeChildAtAlongMainAxis(viewIndex, j)) {\n                    int dividerTop;\n                    if (fromBottomToTop) {\n                        dividerTop = view.getBottom() + lp.bottomMargin;\n                    } else {\n                        dividerTop = view.getTop() - lp.topMargin - mDividerHorizontalHeight;\n                    }\n\n                    drawHorizontalDivider(canvas, flexLine.mLeft, dividerTop, flexLine.mCrossSize);\n                }\n\n                // Judge if the end divider is needed\n                if (j == flexLine.mItemCount - 1) {\n                    if ((mShowDividerHorizontal & SHOW_DIVIDER_END) > 0) {\n                        int dividerTop;\n                        if (fromBottomToTop) {\n                            dividerTop = view.getTop() - lp.topMargin - mDividerHorizontalHeight;\n                        } else {\n                            dividerTop = view.getBottom() + lp.bottomMargin;\n                        }\n\n                        drawHorizontalDivider(canvas, flexLine.mLeft, dividerTop,\n                                flexLine.mCrossSize);\n                    }\n                }\n            }\n\n            // Judge if the beginning or middle dividers are needed before the flex line\n            if (hasDividerBeforeFlexLine(i)) {\n                int verticalDividerLeft;\n                if (isRtl) {\n                    verticalDividerLeft = flexLine.mRight;\n                } else {\n                    verticalDividerLeft = flexLine.mLeft - mDividerVerticalWidth;\n                }\n                drawVerticalDivider(canvas, verticalDividerLeft, paddingTop,\n                        verticalDividerLength);\n            }\n            if (hasEndDividerAfterFlexLine(i)) {\n                if ((mShowDividerVertical & SHOW_DIVIDER_END) > 0) {\n                    int verticalDividerLeft;\n                    if (isRtl) {\n                        verticalDividerLeft = flexLine.mLeft - mDividerVerticalWidth;\n                    } else {\n                        verticalDividerLeft = flexLine.mRight;\n                    }\n                    drawVerticalDivider(canvas, verticalDividerLeft, paddingTop,\n                            verticalDividerLength);\n                }\n            }\n        }\n    }\n\n    private void drawVerticalDivider(Canvas canvas, int left, int top, int length) {\n        if (mDividerDrawableVertical == null) {\n            return;\n        }\n        mDividerDrawableVertical.setBounds(left, top, left + mDividerVerticalWidth, top + length);\n        mDividerDrawableVertical.draw(canvas);\n    }\n\n    private void drawHorizontalDivider(Canvas canvas, int left, int top, int length) {\n        if (mDividerDrawableHorizontal == null) {\n            return;\n        }\n        mDividerDrawableHorizontal\n                .setBounds(left, top, left + length, top + mDividerHorizontalHeight);\n        mDividerDrawableHorizontal.draw(canvas);\n    }\n\n    @Override\n    protected boolean checkLayoutParams(ViewGroup.LayoutParams p) {\n        return p instanceof FlexboxLayout.LayoutParams;\n    }\n\n    @Override\n    public LayoutParams generateLayoutParams(AttributeSet attrs) {\n        return new FlexboxLayout.LayoutParams(getContext(), attrs);\n    }\n\n    @Override\n    protected ViewGroup.LayoutParams generateLayoutParams(ViewGroup.LayoutParams lp) {\n        if (lp instanceof FlexboxLayout.LayoutParams) {\n            return new FlexboxLayout.LayoutParams((FlexboxLayout.LayoutParams) lp);\n        } else if (lp instanceof MarginLayoutParams) {\n            return new FlexboxLayout.LayoutParams((MarginLayoutParams) lp);\n        }\n        return new LayoutParams(lp);\n    }\n\n    @FlexDirection\n    @Override\n    public int getFlexDirection() {\n        return mFlexDirection;\n    }\n\n    @Override\n    public void setFlexDirection(@FlexDirection int flexDirection) {\n        if (mFlexDirection != flexDirection) {\n            mFlexDirection = flexDirection;\n            requestLayout();\n        }\n    }\n\n    @FlexWrap\n    @Override\n    public int getFlexWrap() {\n        return mFlexWrap;\n    }\n\n    @Override\n    public void setFlexWrap(@FlexWrap int flexWrap) {\n        if (mFlexWrap != flexWrap) {\n            mFlexWrap = flexWrap;\n            requestLayout();\n        }\n    }\n\n    @JustifyContent\n    @Override\n    public int getJustifyContent() {\n        return mJustifyContent;\n    }\n\n    @Override\n    public void setJustifyContent(@JustifyContent int justifyContent) {\n        if (mJustifyContent != justifyContent) {\n            mJustifyContent = justifyContent;\n            requestLayout();\n        }\n    }\n\n    @AlignItems\n    @Override\n    public int getAlignItems() {\n        return mAlignItems;\n    }\n\n    @Override\n    public void setAlignItems(@AlignItems int alignItems) {\n        if (mAlignItems != alignItems) {\n            mAlignItems = alignItems;\n            requestLayout();\n        }\n    }\n\n    @AlignContent\n    @Override\n    public int getAlignContent() {\n        return mAlignContent;\n    }\n\n    @Override\n    public void setAlignContent(@AlignContent int alignContent) {\n        if (mAlignContent != alignContent) {\n            mAlignContent = alignContent;\n            requestLayout();\n        }\n    }\n\n    @Override\n    public int getMaxLine() {\n        return mMaxLine;\n    }\n\n    @Override\n    public void setMaxLine(int maxLine) {\n        if (mMaxLine != maxLine) {\n            mMaxLine = maxLine;\n            requestLayout();\n        }\n    }\n\n    /**\n     * @return the flex lines composing this flex container. This method returns a copy of the\n     * original list excluding a dummy flex line (flex line that doesn't have any flex items in it\n     * but used for the alignment along the cross axis).\n     * Thus any changes of the returned list are not reflected to the original list.\n     */\n    @Override\n    public List<FlexLine> getFlexLines() {\n        List<FlexLine> result = new ArrayList<>(mFlexLines.size());\n        for (FlexLine flexLine : mFlexLines) {\n            if (flexLine.getItemCountNotGone() == 0) {\n                continue;\n            }\n            result.add(flexLine);\n        }\n        return result;\n    }\n\n    @Override\n    public int getDecorationLengthMainAxis(View view, int index, int indexInFlexLine) {\n        int decorationLength = 0;\n        if (isMainAxisDirectionHorizontal()) {\n            if (hasDividerBeforeChildAtAlongMainAxis(index, indexInFlexLine)) {\n                decorationLength += mDividerVerticalWidth;\n            }\n            if ((mShowDividerVertical & SHOW_DIVIDER_END) > 0) {\n                decorationLength += mDividerVerticalWidth;\n            }\n        } else {\n            if (hasDividerBeforeChildAtAlongMainAxis(index, indexInFlexLine)) {\n                decorationLength += mDividerHorizontalHeight;\n            }\n            if ((mShowDividerHorizontal & SHOW_DIVIDER_END) > 0) {\n                decorationLength += mDividerHorizontalHeight;\n            }\n        }\n        return decorationLength;\n    }\n\n    @Override\n    public int getDecorationLengthCrossAxis(View view) {\n        // Decoration along the cross axis for an individual view is not supported in the\n        // FlexboxLayout.\n        return 0;\n    }\n\n    @Override\n    public void onNewFlexLineAdded(FlexLine flexLine) {\n        // The size of the end divider isn't added until the flexLine is added to the flex container\n        // take the divider width (or height) into account when adding the flex line.\n        if (isMainAxisDirectionHorizontal()) {\n            if ((mShowDividerVertical & SHOW_DIVIDER_END) > 0) {\n                flexLine.mMainSize += mDividerVerticalWidth;\n                flexLine.mDividerLengthInMainSize += mDividerVerticalWidth;\n            }\n        } else {\n            if ((mShowDividerHorizontal & SHOW_DIVIDER_END) > 0) {\n                flexLine.mMainSize += mDividerHorizontalHeight;\n                flexLine.mDividerLengthInMainSize += mDividerHorizontalHeight;\n            }\n        }\n    }\n\n    @Override\n    public int getChildWidthMeasureSpec(int widthSpec, int padding, int childDimension) {\n        return getChildMeasureSpec(widthSpec, padding, childDimension);\n    }\n\n    @Override\n    public int getChildHeightMeasureSpec(int heightSpec, int padding, int childDimension) {\n        return getChildMeasureSpec(heightSpec, padding, childDimension);\n    }\n\n    @Override\n    public void onNewFlexItemAdded(View view, int index, int indexInFlexLine, FlexLine flexLine) {\n        // Check if the beginning or middle divider is required for the flex item\n        if (hasDividerBeforeChildAtAlongMainAxis(index, indexInFlexLine)) {\n            if (isMainAxisDirectionHorizontal()) {\n                flexLine.mMainSize += mDividerVerticalWidth;\n                flexLine.mDividerLengthInMainSize += mDividerVerticalWidth;\n            } else {\n                flexLine.mMainSize += mDividerHorizontalHeight;\n                flexLine.mDividerLengthInMainSize += mDividerHorizontalHeight;\n            }\n        }\n    }\n\n    @Override\n    public void setFlexLines(List<FlexLine> flexLines) {\n        mFlexLines = flexLines;\n    }\n\n    @Override\n    public List<FlexLine> getFlexLinesInternal() {\n        return mFlexLines;\n    }\n\n    @Override\n    public void updateViewCache(int position, View view) {\n        // No op\n    }\n\n    /**\n     * @return the horizontal divider drawable that will divide each item.\n     * @see #setDividerDrawable(Drawable)\n     * @see #setDividerDrawableHorizontal(Drawable)\n     */\n    @Nullable\n    @SuppressWarnings(\"UnusedDeclaration\")\n    public Drawable getDividerDrawableHorizontal() {\n        return mDividerDrawableHorizontal;\n    }\n\n    /**\n     * @return the vertical divider drawable that will divide each item.\n     * @see #setDividerDrawable(Drawable)\n     * @see #setDividerDrawableVertical(Drawable)\n     */\n    @Nullable\n    @SuppressWarnings(\"UnusedDeclaration\")\n    public Drawable getDividerDrawableVertical() {\n        return mDividerDrawableVertical;\n    }\n\n    /**\n     * Set a drawable to be used as a divider between items. The drawable is used for both\n     * horizontal and vertical dividers.\n     *\n     * @param divider Drawable that will divide each item for both horizontally and vertically.\n     * @see #setShowDivider(int)\n     */\n    public void setDividerDrawable(Drawable divider) {\n        setDividerDrawableHorizontal(divider);\n        setDividerDrawableVertical(divider);\n    }\n\n    /**\n     * Set a drawable to be used as a horizontal divider between items.\n     *\n     * @param divider Drawable that will divide each item.\n     * @see #setDividerDrawable(Drawable)\n     * @see #setShowDivider(int)\n     * @see #setShowDividerHorizontal(int)\n     */\n    public void setDividerDrawableHorizontal(@Nullable Drawable divider) {\n        if (divider == mDividerDrawableHorizontal) {\n            return;\n        }\n        mDividerDrawableHorizontal = divider;\n        if (divider != null) {\n            mDividerHorizontalHeight = divider.getIntrinsicHeight();\n        } else {\n            mDividerHorizontalHeight = 0;\n        }\n        setWillNotDrawFlag();\n        requestLayout();\n    }\n\n    /**\n     * Set a drawable to be used as a vertical divider between items.\n     *\n     * @param divider Drawable that will divide each item.\n     * @see #setDividerDrawable(Drawable)\n     * @see #setShowDivider(int)\n     * @see #setShowDividerVertical(int)\n     */\n    public void setDividerDrawableVertical(@Nullable Drawable divider) {\n        if (divider == mDividerDrawableVertical) {\n            return;\n        }\n        mDividerDrawableVertical = divider;\n        if (divider != null) {\n            mDividerVerticalWidth = divider.getIntrinsicWidth();\n        } else {\n            mDividerVerticalWidth = 0;\n        }\n        setWillNotDrawFlag();\n        requestLayout();\n    }\n\n    @FlexboxLayout.DividerMode\n    public int getShowDividerVertical() {\n        return mShowDividerVertical;\n    }\n\n    @FlexboxLayout.DividerMode\n    public int getShowDividerHorizontal() {\n        return mShowDividerHorizontal;\n    }\n\n    /**\n     * Set how dividers should be shown between items in this layout. This method sets the\n     * divider mode for both horizontally and vertically.\n     *\n     * @param dividerMode One or more of {@link #SHOW_DIVIDER_BEGINNING},\n     *                    {@link #SHOW_DIVIDER_MIDDLE}, or {@link #SHOW_DIVIDER_END},\n     *                    or {@link #SHOW_DIVIDER_NONE} to show no dividers.\n     * @see #setShowDividerVertical(int)\n     * @see #setShowDividerHorizontal(int)\n     */\n    public void setShowDivider(@DividerMode int dividerMode) {\n        setShowDividerVertical(dividerMode);\n        setShowDividerHorizontal(dividerMode);\n    }\n\n    /**\n     * Set how vertical dividers should be shown between items in this layout\n     *\n     * @param dividerMode One or more of {@link #SHOW_DIVIDER_BEGINNING},\n     *                    {@link #SHOW_DIVIDER_MIDDLE}, or {@link #SHOW_DIVIDER_END},\n     *                    or {@link #SHOW_DIVIDER_NONE} to show no dividers.\n     * @see #setShowDivider(int)\n     */\n    public void setShowDividerVertical(@DividerMode int dividerMode) {\n        if (dividerMode != mShowDividerVertical) {\n            mShowDividerVertical = dividerMode;\n            requestLayout();\n        }\n    }\n\n    /**\n     * Set how horizontal dividers should be shown between items in this layout.\n     *\n     * @param dividerMode One or more of {@link #SHOW_DIVIDER_BEGINNING},\n     *                    {@link #SHOW_DIVIDER_MIDDLE}, or {@link #SHOW_DIVIDER_END},\n     *                    or {@link #SHOW_DIVIDER_NONE} to show no dividers.\n     * @see #setShowDivider(int)\n     */\n    public void setShowDividerHorizontal(@DividerMode int dividerMode) {\n        if (dividerMode != mShowDividerHorizontal) {\n            mShowDividerHorizontal = dividerMode;\n            requestLayout();\n        }\n    }\n\n    private void setWillNotDrawFlag() {\n        if (mDividerDrawableHorizontal == null && mDividerDrawableVertical == null) {\n            setWillNotDraw(true);\n        } else {\n            setWillNotDraw(false);\n        }\n    }\n\n    /**\n     * Check if a divider is needed before the view whose indices are passed as arguments.\n     *\n     * @param index           the absolute index of the view to be judged\n     * @param indexInFlexLine the relative index in the flex line where the view\n     *                        belongs\n     * @return {@code true} if a divider is needed, {@code false} otherwise\n     */\n    private boolean hasDividerBeforeChildAtAlongMainAxis(int index, int indexInFlexLine) {\n        if (allViewsAreGoneBefore(index, indexInFlexLine)) {\n            if (isMainAxisDirectionHorizontal()) {\n                return (mShowDividerVertical & SHOW_DIVIDER_BEGINNING) != 0;\n            } else {\n                return (mShowDividerHorizontal & SHOW_DIVIDER_BEGINNING) != 0;\n            }\n        } else {\n            if (isMainAxisDirectionHorizontal()) {\n                return (mShowDividerVertical & SHOW_DIVIDER_MIDDLE) != 0;\n            } else {\n                return (mShowDividerHorizontal & SHOW_DIVIDER_MIDDLE) != 0;\n            }\n        }\n    }\n\n    private boolean allViewsAreGoneBefore(int index, int indexInFlexLine) {\n        for (int i = 1; i <= indexInFlexLine; i++) {\n            View view = getReorderedChildAt(index - i);\n            if (view != null && view.getVisibility() != View.GONE) {\n                return false;\n            }\n        }\n        return true;\n    }\n\n    /**\n     * Check if a divider is needed before the flex line whose index is passed as an argument.\n     *\n     * @param flexLineIndex the index of the flex line to be checked\n     * @return {@code true} if a divider is needed, {@code false} otherwise\n     */\n    private boolean hasDividerBeforeFlexLine(int flexLineIndex) {\n        if (flexLineIndex < 0 || flexLineIndex >= mFlexLines.size()) {\n            return false;\n        }\n        if (allFlexLinesAreDummyBefore(flexLineIndex)) {\n            if (isMainAxisDirectionHorizontal()) {\n                return (mShowDividerHorizontal & SHOW_DIVIDER_BEGINNING) != 0;\n            } else {\n                return (mShowDividerVertical & SHOW_DIVIDER_BEGINNING) != 0;\n            }\n        } else {\n            if (isMainAxisDirectionHorizontal()) {\n                return (mShowDividerHorizontal & SHOW_DIVIDER_MIDDLE) != 0;\n            } else {\n                return (mShowDividerVertical & SHOW_DIVIDER_MIDDLE) != 0;\n            }\n        }\n    }\n\n    private boolean allFlexLinesAreDummyBefore(int flexLineIndex) {\n        for (int i = 0; i < flexLineIndex; i++) {\n            if (mFlexLines.get(i).getItemCountNotGone() > 0) {\n                return false;\n            }\n        }\n        return true;\n    }\n\n    /**\n     * Check if a end divider is needed after the flex line whose index is passed as an argument.\n     *\n     * @param flexLineIndex the index of the flex line to be checked\n     * @return {@code true} if a divider is needed, {@code false} otherwise\n     */\n    private boolean hasEndDividerAfterFlexLine(int flexLineIndex) {\n        if (flexLineIndex < 0 || flexLineIndex >= mFlexLines.size()) {\n            return false;\n        }\n\n        for (int i = flexLineIndex + 1; i < mFlexLines.size(); i++) {\n            if (mFlexLines.get(i).getItemCountNotGone() > 0) {\n                return false;\n            }\n        }\n        if (isMainAxisDirectionHorizontal()) {\n            return (mShowDividerHorizontal & SHOW_DIVIDER_END) != 0;\n        } else {\n            return (mShowDividerVertical & SHOW_DIVIDER_END) != 0;\n        }\n\n    }\n\n    /**\n     * Per child parameters for children views of the {@link FlexboxLayout}.\n     *\n     * Note that some parent fields (which are not primitive nor a class implements\n     * {@link Parcelable}) are not included as the stored/restored fields after this class\n     * is serialized/de-serialized as an {@link Parcelable}.\n     */\n    public static class LayoutParams extends ViewGroup.MarginLayoutParams implements FlexItem {\n\n        /**\n         * @see FlexItem#getOrder()\n         */\n        private int mOrder = FlexItem.ORDER_DEFAULT;\n\n        /**\n         * @see FlexItem#getFlexGrow()\n         */\n        private float mFlexGrow = FlexItem.FLEX_GROW_DEFAULT;\n\n        /**\n         * @see FlexItem#getFlexShrink()\n         */\n        private float mFlexShrink = FlexItem.FLEX_SHRINK_DEFAULT;\n\n        /**\n         * @see FlexItem#getAlignSelf()\n         */\n        private int mAlignSelf = AlignSelf.AUTO;\n\n        /**\n         * @see FlexItem#getFlexBasisPercent()\n         */\n        private float mFlexBasisPercent = FlexItem.FLEX_BASIS_PERCENT_DEFAULT;\n\n        /**\n         * @see FlexItem#getMinWidth()\n         */\n        private int mMinWidth = NOT_SET;\n\n        /**\n         * @see FlexItem#getMinHeight()\n         */\n        private int mMinHeight = NOT_SET;\n\n        /**\n         * @see FlexItem#getMaxWidth()\n         */\n        private int mMaxWidth = MAX_SIZE;\n\n        /**\n         * @see FlexItem#getMaxHeight()\n         */\n        private int mMaxHeight = MAX_SIZE;\n\n        /**\n         * @see FlexItem#isWrapBefore()\n         */\n        private boolean mWrapBefore;\n\n        public LayoutParams(Context context, AttributeSet attrs) {\n            super(context, attrs);\n\n            TypedArray a = context\n                    .obtainStyledAttributes(attrs, R.styleable.FlexboxLayout_Layout);\n            mOrder = a.getInt(R.styleable.FlexboxLayout_Layout_layout_order, ORDER_DEFAULT);\n            mFlexGrow = a\n                    .getFloat(R.styleable.FlexboxLayout_Layout_layout_flexGrow, FLEX_GROW_DEFAULT);\n            mFlexShrink = a.getFloat(R.styleable.FlexboxLayout_Layout_layout_flexShrink,\n                    FLEX_SHRINK_DEFAULT);\n            mAlignSelf = a\n                    .getInt(R.styleable.FlexboxLayout_Layout_layout_alignSelf, AlignSelf.AUTO);\n            mFlexBasisPercent = a\n                    .getFraction(R.styleable.FlexboxLayout_Layout_layout_flexBasisPercent, 1, 1,\n                            FLEX_BASIS_PERCENT_DEFAULT);\n            mMinWidth = a\n                    .getDimensionPixelSize(R.styleable.FlexboxLayout_Layout_layout_minWidth, NOT_SET);\n            mMinHeight = a\n                    .getDimensionPixelSize(R.styleable.FlexboxLayout_Layout_layout_minHeight, NOT_SET);\n            mMaxWidth = a.getDimensionPixelSize(R.styleable.FlexboxLayout_Layout_layout_maxWidth,\n                    MAX_SIZE);\n            mMaxHeight = a.getDimensionPixelSize(R.styleable.FlexboxLayout_Layout_layout_maxHeight,\n                    MAX_SIZE);\n            mWrapBefore = a.getBoolean(R.styleable.FlexboxLayout_Layout_layout_wrapBefore, false);\n            a.recycle();\n        }\n\n        public LayoutParams(LayoutParams source) {\n            super(source);\n\n            mOrder = source.mOrder;\n            mFlexGrow = source.mFlexGrow;\n            mFlexShrink = source.mFlexShrink;\n            mAlignSelf = source.mAlignSelf;\n            mFlexBasisPercent = source.mFlexBasisPercent;\n            mMinWidth = source.mMinWidth;\n            mMinHeight = source.mMinHeight;\n            mMaxWidth = source.mMaxWidth;\n            mMaxHeight = source.mMaxHeight;\n            mWrapBefore = source.mWrapBefore;\n        }\n\n        public LayoutParams(ViewGroup.LayoutParams source) {\n            super(source);\n        }\n\n        public LayoutParams(int width, int height) {\n            super(new ViewGroup.LayoutParams(width, height));\n        }\n\n        public LayoutParams(MarginLayoutParams source) {\n            super(source);\n        }\n\n        @Override\n        public int getWidth() {\n            return width;\n        }\n\n        @Override\n        public void setWidth(int width) {\n            this.width = width;\n        }\n\n        @Override\n        public int getHeight() {\n            return height;\n        }\n\n        @Override\n        public void setHeight(int height) {\n            this.height = height;\n        }\n\n        @Override\n        public int getOrder() {\n            return mOrder;\n        }\n\n        @Override\n        public void setOrder(int order) {\n            mOrder = order;\n        }\n\n        @Override\n        public float getFlexGrow() {\n            return mFlexGrow;\n        }\n\n        @Override\n        public void setFlexGrow(float flexGrow) {\n            this.mFlexGrow = flexGrow;\n        }\n\n        @Override\n        public float getFlexShrink() {\n            return mFlexShrink;\n        }\n\n        @Override\n        public void setFlexShrink(float flexShrink) {\n            this.mFlexShrink = flexShrink;\n        }\n\n        @AlignSelf\n        @Override\n        public int getAlignSelf() {\n            return mAlignSelf;\n        }\n\n        @Override\n        public void setAlignSelf(@AlignSelf int alignSelf) {\n            this.mAlignSelf = alignSelf;\n        }\n\n        @Override\n        public int getMinWidth() {\n            return mMinWidth;\n        }\n\n        @Override\n        public void setMinWidth(int minWidth) {\n            this.mMinWidth = minWidth;\n        }\n\n        @Override\n        public int getMinHeight() {\n            return mMinHeight;\n        }\n\n        @Override\n        public void setMinHeight(int minHeight) {\n            this.mMinHeight = minHeight;\n        }\n\n        @Override\n        public int getMaxWidth() {\n            return mMaxWidth;\n        }\n\n        @Override\n        public void setMaxWidth(int maxWidth) {\n            this.mMaxWidth = maxWidth;\n        }\n\n        @Override\n        public int getMaxHeight() {\n            return mMaxHeight;\n        }\n\n        @Override\n        public void setMaxHeight(int maxHeight) {\n            this.mMaxHeight = maxHeight;\n        }\n\n        @Override\n        public boolean isWrapBefore() {\n            return mWrapBefore;\n        }\n\n        @Override\n        public void setWrapBefore(boolean wrapBefore) {\n            this.mWrapBefore = wrapBefore;\n        }\n\n        @Override\n        public float getFlexBasisPercent() {\n            return mFlexBasisPercent;\n        }\n\n        @Override\n        public void setFlexBasisPercent(float flexBasisPercent) {\n            this.mFlexBasisPercent = flexBasisPercent;\n        }\n\n        @Override\n        public int getMarginLeft() {\n            return leftMargin;\n        }\n\n        @Override\n        public int getMarginTop() {\n            return topMargin;\n        }\n\n        @Override\n        public int getMarginRight() {\n            return rightMargin;\n        }\n\n        @Override\n        public int getMarginBottom() {\n            return bottomMargin;\n        }\n\n        @Override\n        public int describeContents() {\n            return 0;\n        }\n\n        @Override\n        public void writeToParcel(Parcel dest, int flags) {\n            dest.writeInt(this.mOrder);\n            dest.writeFloat(this.mFlexGrow);\n            dest.writeFloat(this.mFlexShrink);\n            dest.writeInt(this.mAlignSelf);\n            dest.writeFloat(this.mFlexBasisPercent);\n            dest.writeInt(this.mMinWidth);\n            dest.writeInt(this.mMinHeight);\n            dest.writeInt(this.mMaxWidth);\n            dest.writeInt(this.mMaxHeight);\n            dest.writeByte(this.mWrapBefore ? (byte) 1 : (byte) 0);\n            dest.writeInt(this.bottomMargin);\n            dest.writeInt(this.leftMargin);\n            dest.writeInt(this.rightMargin);\n            dest.writeInt(this.topMargin);\n            dest.writeInt(this.height);\n            dest.writeInt(this.width);\n        }\n\n        protected LayoutParams(Parcel in) {\n            // Passing a resolved value to resolve a lint warning\n            // height and width are set in this method anyway.\n            super(0, 0);\n            this.mOrder = in.readInt();\n            this.mFlexGrow = in.readFloat();\n            this.mFlexShrink = in.readFloat();\n            this.mAlignSelf = in.readInt();\n            this.mFlexBasisPercent = in.readFloat();\n            this.mMinWidth = in.readInt();\n            this.mMinHeight = in.readInt();\n            this.mMaxWidth = in.readInt();\n            this.mMaxHeight = in.readInt();\n            this.mWrapBefore = in.readByte() != 0;\n            this.bottomMargin = in.readInt();\n            this.leftMargin = in.readInt();\n            this.rightMargin = in.readInt();\n            this.topMargin = in.readInt();\n            this.height = in.readInt();\n            this.width = in.readInt();\n        }\n\n        public static final Parcelable.Creator<LayoutParams> CREATOR\n                = new Parcelable.Creator<LayoutParams>() {\n            @Override\n            public LayoutParams createFromParcel(Parcel source) {\n                return new LayoutParams(source);\n            }\n\n            @Override\n            public LayoutParams[] newArray(int size) {\n                return new LayoutParams[size];\n            }\n        };\n    }\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/FlexboxLayoutManager.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport static androidx.recyclerview.widget.LinearLayoutManager.INVALID_OFFSET;\nimport static androidx.recyclerview.widget.RecyclerView.NO_POSITION;\n\nimport android.content.Context;\nimport android.graphics.PointF;\nimport android.graphics.Rect;\nimport android.os.Parcel;\nimport android.os.Parcelable;\nimport android.util.AttributeSet;\nimport android.util.Log;\nimport android.util.SparseArray;\nimport android.view.View;\nimport android.view.ViewGroup;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport androidx.annotation.NonNull;\nimport androidx.core.view.ViewCompat;\nimport androidx.recyclerview.widget.LinearLayoutManager;\nimport androidx.recyclerview.widget.LinearSmoothScroller;\nimport androidx.recyclerview.widget.OrientationHelper;\nimport androidx.recyclerview.widget.RecyclerView;\n\n/**\n * LayoutManager for the {@link RecyclerView}. This class is intended to be used within a\n * {@link RecyclerView} and offers the same capabilities of measure/layout its children\n * as the {@link FlexboxLayout}.\n */\npublic class FlexboxLayoutManager extends RecyclerView.LayoutManager implements FlexContainer,\n        RecyclerView.SmoothScroller.ScrollVectorProvider {\n\n    private static final String TAG = \"FlexboxLayoutManager\";\n\n    /**\n     * Temporary Rect instance to be passed to\n     * {@link RecyclerView.LayoutManager#calculateItemDecorationsForChild}\n     * to avoid creating a Rect instance every time.\n     */\n    private static final Rect TEMP_RECT = new Rect();\n\n    private static final boolean DEBUG = false;\n\n    /**\n     * The current value of the {@link FlexDirection}, the default value is {@link\n     * FlexDirection#ROW}.\n     *\n     * @see FlexContainer#getFlexDirection()\n     */\n    private int mFlexDirection;\n\n    /**\n     * The current value of the {@link FlexWrap}, the default value is {@link FlexWrap#WRAP}.\n     *\n     * @see FlexContainer#getFlexWrap()\n     */\n    private int mFlexWrap;\n\n    /**\n     * The current value of the {@link JustifyContent}, the default value is\n     * {@link JustifyContent#FLEX_START}.\n     *\n     * @see FlexContainer#getJustifyContent()\n     */\n    private int mJustifyContent;\n\n    /**\n     * The current value of the {@link AlignItems}, the default value is\n     * {@link AlignItems#STRETCH}.\n     *\n     * @see FlexContainer#getAlignItems()\n     */\n    private int mAlignItems;\n\n    private int mMaxLine = NOT_SET;\n\n    /**\n     * True if the layout direction is right to left, false otherwise.\n     */\n    private boolean mIsRtl;\n\n    /**\n     * True if the layout direction is bottom to top, false otherwise.\n     */\n    private boolean mFromBottomToTop;\n\n    private List<FlexLine> mFlexLines = new ArrayList<>();\n\n    private final FlexboxHelper mFlexboxHelper = new FlexboxHelper(this);\n\n    /**\n     * A snapshot of the {@link RecyclerView.Recycler} instance at a given moment.\n     * It's not guaranteed that this instance has a reference to the latest Recycler.\n     * When you want to use the latest Recycler, use the one passed as an method argument\n     * (such as the one in {@link #onLayoutChildren(RecyclerView.Recycler, RecyclerView.State)})\n     */\n    private RecyclerView.Recycler mRecycler;\n\n    /**\n     * A snapshot of the {@link RecyclerView.State} instance at a given moment.\n     * It's not guaranteed that this instance has a reference to the latest State.\n     * When you want to use the latest State, use the one passed as an method argument\n     * (such as the one in {@link #onLayoutChildren(RecyclerView.Recycler, RecyclerView.State)})\n     */\n    private RecyclerView.State mState;\n\n    private LayoutState mLayoutState;\n\n    private AnchorInfo mAnchorInfo = new AnchorInfo();\n\n    /**\n     * {@link OrientationHelper} along cross axis, which will be the primary scrolling direction.\n     * e.g. If the flex direction is set to {@link FlexDirection#ROW} and flex wrap is set to\n     * {@link FlexWrap#WRAP}, the RecyclerView scrolls vertically (along the cross axis).\n     */\n    private OrientationHelper mOrientationHelper;\n\n    /**\n     * {@link OrientationHelper} along the main axis, which will be the secondary scrolling\n     * direction if the size of the main size is larger than the parent of the RecyclerView.\n     */\n    private OrientationHelper mSubOrientationHelper;\n\n    private SavedState mPendingSavedState;\n\n    /**\n     * The position to which the next layout should start from this adapter position.\n     * This value is set either from the {@link #mPendingSavedState} when a configuration change\n     * happens or programmatically such as when the {@link #scrollToPosition(int)} is called.\n     */\n    private int mPendingScrollPosition = NO_POSITION;\n\n    /**\n     * The offset by which the next layout should be offset.\n     */\n    private int mPendingScrollPositionOffset = INVALID_OFFSET;\n\n    /**\n     * The width value used in the last {@link #onLayoutChildren} method.\n     */\n    private int mLastWidth = Integer.MIN_VALUE;\n\n    /**\n     * The height value used in the last {@link #onLayoutChildren} method.\n     */\n    private int mLastHeight = Integer.MIN_VALUE;\n\n    /**\n     * If set to {@code true}, this LayoutManager tries to recycle the children when detached from\n     * the RecyclerView so that recycled views can be reused using RecycledViewPool.\n     */\n    private boolean mRecycleChildrenOnDetach;\n\n    /**\n     * View cache within this LayoutManager. This is used to avoid the same ViewHolder is created\n     * multiple times in the same layout pass (onLayoutChildren or scrollHorizontally or\n     * scrollVertically).\n     * The keys and values in this cache needs to be cleared at the end of each layout pass.\n     */\n    private SparseArray<View> mViewCache = new SparseArray<>();\n\n    private final Context mContext;\n\n    /** The reference to the parent of the RecyclerView */\n    private View mParent;\n\n    /**\n     * Indicates the position that the view position that the flex line which has the view having\n     * this position needs to be recomputed before the next layout.\n     * For example, this is updated when a new View is inserted into the position before the\n     * first visible position.\n     */\n    private int mDirtyPosition = NO_POSITION;\n\n    /**\n     * Used for storing the results of calculation of flex lines to avoid creating a new instance\n     * every time the calculation happens.\n     */\n    private FlexboxHelper.FlexLinesResult mFlexLinesResult = new FlexboxHelper.FlexLinesResult();\n\n    /**\n     * Creates a default FlexboxLayoutManager.\n     */\n    public FlexboxLayoutManager(Context context) {\n        this(context, FlexDirection.ROW, FlexWrap.WRAP);\n    }\n\n    /**\n     * Creates a FlexboxLayoutManager with the flexDirection specified.\n     *\n     * @param flexDirection the flex direction attribute\n     */\n    public FlexboxLayoutManager(Context context, @FlexDirection int flexDirection) {\n        this(context, flexDirection, FlexWrap.WRAP);\n    }\n\n    /**\n     * Creates a FlexboxLayoutManager with the flexDirection and flexWrap attributes specified.\n     *\n     * @param flexDirection the flex direction attribute\n     * @param flexWrap      the flex wrap attribute\n     */\n    public FlexboxLayoutManager(Context context, @FlexDirection int flexDirection,\n            @FlexWrap int flexWrap) {\n        setFlexDirection(flexDirection);\n        setFlexWrap(flexWrap);\n        setAlignItems(AlignItems.STRETCH);\n        mContext = context;\n    }\n\n    /**\n     * Constructor used when layout manager is set in XML by RecyclerView attribute\n     * \"layoutManager\". No corresponding attributes for the {@code orientation},\n     * {@code reverseLayout} and {@code stackFromEnd} exist in Flexbox, thus map the similar\n     * attributes from Flexbox that behave similarly for each of them.\n     *\n     * {@code android:orientation} maps to the {@link FlexDirection},\n     * HORIZONTAL -> {@link FlexDirection#ROW}, VERTICAL -> {@link FlexDirection#COLUMN}.\n     *\n     * {@code android.support.v7.recyclerview:reverseLayout} reverses the direction of the\n     * {@link FlexDirection}, i.e. if reverseLayout is {@code true}, {@link FlexDirection#ROW} is\n     * changed to {@link FlexDirection#ROW_REVERSE}. Similarly {@link FlexDirection#COLUMN} is\n     * changed to {@link FlexDirection#COLUMN_REVERSE}.\n     */\n    public FlexboxLayoutManager(Context context, AttributeSet attrs, int defStyleAttr,\n            int defStyleRes) {\n        Properties properties = getProperties(context, attrs, defStyleAttr, defStyleRes);\n        switch (properties.orientation) {\n            case LinearLayoutManager.HORIZONTAL:\n                if (properties.reverseLayout) {\n                    setFlexDirection(FlexDirection.ROW_REVERSE);\n                } else {\n                    setFlexDirection(FlexDirection.ROW);\n                }\n                break;\n            case LinearLayoutManager.VERTICAL:\n                if (properties.reverseLayout) {\n                    setFlexDirection(FlexDirection.COLUMN_REVERSE);\n                } else {\n                    setFlexDirection(FlexDirection.COLUMN);\n                }\n                break;\n        }\n        setFlexWrap(FlexWrap.WRAP);\n        setAlignItems(AlignItems.STRETCH);\n        mContext = context;\n    }\n\n    @Override\n    public boolean isAutoMeasureEnabled() {\n        return true;\n    }\n\n    // From here, methods from FlexContainer\n    @FlexDirection\n    @Override\n    public int getFlexDirection() {\n        return mFlexDirection;\n    }\n\n    @Override\n    public void setFlexDirection(@FlexDirection int flexDirection) {\n        if (mFlexDirection != flexDirection) {\n            // Remove the existing views even if the direction changes from\n            // row -> row_reverse or column -> column_reverse to make the item decorations dirty\n            // state\n            removeAllViews();\n            mFlexDirection = flexDirection;\n            mOrientationHelper = null;\n            mSubOrientationHelper = null;\n            clearFlexLines();\n            requestLayout();\n        }\n    }\n\n    @Override\n    @FlexWrap\n    public int getFlexWrap() {\n        return mFlexWrap;\n    }\n\n    @Override\n    public void setFlexWrap(@FlexWrap int flexWrap) {\n        if (flexWrap == FlexWrap.WRAP_REVERSE) {\n            throw new UnsupportedOperationException(\"wrap_reverse is not supported in \"\n                    + \"FlexboxLayoutManager\");\n        }\n        if (mFlexWrap != flexWrap) {\n            if (mFlexWrap == FlexWrap.NOWRAP || flexWrap == FlexWrap.NOWRAP) {\n                removeAllViews();\n                clearFlexLines();\n            }\n            mFlexWrap = flexWrap;\n            mOrientationHelper = null;\n            mSubOrientationHelper = null;\n            requestLayout();\n        }\n    }\n\n    @JustifyContent\n    @Override\n    public int getJustifyContent() {\n        return mJustifyContent;\n    }\n\n    @Override\n    public void setJustifyContent(@JustifyContent int justifyContent) {\n        if (mJustifyContent != justifyContent) {\n            mJustifyContent = justifyContent;\n            requestLayout();\n        }\n    }\n\n    @AlignItems\n    @Override\n    public int getAlignItems() {\n        return mAlignItems;\n    }\n\n    @Override\n    public void setAlignItems(@AlignItems int alignItems) {\n        if (mAlignItems != alignItems) {\n            if (mAlignItems == AlignItems.STRETCH || alignItems == AlignItems.STRETCH) {\n                removeAllViews();\n                clearFlexLines();\n            }\n            mAlignItems = alignItems;\n            requestLayout();\n        }\n    }\n\n    @AlignContent\n    @Override\n    public int getAlignContent() {\n        return AlignContent.STRETCH;\n    }\n\n    @Override\n    public void setAlignContent(@AlignContent int alignContent) {\n        throw new UnsupportedOperationException(\"Setting the alignContent in the \"\n                + \"FlexboxLayoutManager is not supported. Use FlexboxLayout \"\n                + \"if you need to use this attribute.\");\n    }\n\n    @Override\n    public int getMaxLine() {\n        return mMaxLine;\n    }\n\n    @Override\n    public void setMaxLine(int maxLine) {\n        if (mMaxLine != maxLine) {\n            mMaxLine = maxLine;\n            requestLayout();\n        }\n    }\n\n    @Override\n    @NonNull\n    public List<FlexLine> getFlexLines() {\n        List<FlexLine> result = new ArrayList<>(mFlexLines.size());\n        for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n            FlexLine flexLine = mFlexLines.get(i);\n            if (flexLine.getItemCount() == 0) {\n                continue;\n            }\n            result.add(flexLine);\n        }\n        return result;\n    }\n\n    @Override\n    public int getDecorationLengthMainAxis(View view, int index, int indexInFlexLine) {\n        if (isMainAxisDirectionHorizontal()) {\n            return getLeftDecorationWidth(view) + getRightDecorationWidth(view);\n        } else {\n            return getTopDecorationHeight(view) + getBottomDecorationHeight(view);\n        }\n    }\n\n    @Override\n    public int getDecorationLengthCrossAxis(View view) {\n        if (isMainAxisDirectionHorizontal()) {\n            return getTopDecorationHeight(view) + getBottomDecorationHeight(view);\n        } else {\n            return getLeftDecorationWidth(view) + getRightDecorationWidth(view);\n        }\n    }\n\n    @Override\n    public void onNewFlexItemAdded(View view, int index, int indexInFlexLine, FlexLine flexLine) {\n        // To avoid creating a new Rect instance every time, passing the same Rect instance\n        // since calculated decorations are assigned to view's LayoutParams inside the\n        // calculateItemDecorationsForChild method anyway.\n        calculateItemDecorationsForChild(view, TEMP_RECT);\n        if (isMainAxisDirectionHorizontal()) {\n            int decorationWidth = getLeftDecorationWidth(view) + getRightDecorationWidth(view);\n            flexLine.mMainSize += decorationWidth;\n            flexLine.mDividerLengthInMainSize += decorationWidth;\n        } else {\n            int decorationHeight = getTopDecorationHeight(view) + getBottomDecorationHeight(view);\n            flexLine.mMainSize += decorationHeight;\n            flexLine.mDividerLengthInMainSize += decorationHeight;\n        }\n    }\n\n    /**\n     * @return the number of flex items contained in the flex container.\n     * This method doesn't always reflect the latest state of the adapter.\n     * If you want to access the latest state of the adapter, use the {@link RecyclerView.State}\n     * instance passed as an argument for some methods (such as\n     * {@link #onLayoutChildren(RecyclerView.Recycler, RecyclerView.State)})\n     *\n     * This method is used to avoid the implementation of the similar method.\n     * i.e. {@link FlexboxLayoutManager#getChildCount()} returns the child count, but it doesn't\n     * include the children that are detached or scrapped.\n     */\n    @Override\n    public int getFlexItemCount() {\n        return mState.getItemCount();\n    }\n\n    /**\n     * @return the flex item as a view specified as the index.\n     * This method doesn't always return the latest state of the view in the adapter.\n     * If you want to access the latest state, use the {@link RecyclerView.Recycler}\n     * instance passed as an argument for some methods (such as\n     * {@link #onLayoutChildren(RecyclerView.Recycler, RecyclerView.State)})\n     *\n     * This method is used to avoid the implementation of the similar method.\n     * i.e. {@link FlexboxLayoutManager#getChildAt(int)} returns a view for the given index,\n     * but the index is based on the layout position, not based on the adapter position, which\n     * isn't desired given the usage of this method.\n     */\n    @Override\n    public View getFlexItemAt(int index) {\n        // Look up the cache within the LayoutManager first, since it's the most light operation.\n        View cachedView = mViewCache.get(index);\n        if (cachedView != null) {\n            return cachedView;\n        }\n        return mRecycler.getViewForPosition(index);\n    }\n\n    /**\n     * Returns a View for the given index.\n     * The order attribute ({@link FlexItem#getOrder()}) is not supported by this class since\n     * otherwise all view holders need to be inflated at least once even though only the visible\n     * part of the layout is needed.\n     * Implementing this method just to make this class conform to the\n     * {@link FlexContainer} interface.\n     *\n     * @param index the index of the view\n     * @return the view for the given index.\n     * If the index is negative or out of bounds of the number of contained views,\n     * returns {@code null}.\n     */\n    @Override\n    public View getReorderedFlexItemAt(int index) {\n        return getFlexItemAt(index);\n    }\n\n    @Override\n    public void onNewFlexLineAdded(FlexLine flexLine) {\n        // No op\n    }\n\n    @Override\n    public int getChildWidthMeasureSpec(int widthSpec, int padding, int childDimension) {\n        return getChildMeasureSpec(getWidth(), getWidthMode(), padding, childDimension,\n                canScrollHorizontally());\n    }\n\n    @Override\n    public int getChildHeightMeasureSpec(int heightSpec, int padding, int childDimension) {\n        return getChildMeasureSpec(getHeight(), getHeightMode(), padding, childDimension,\n                canScrollVertically());\n    }\n\n    @Override\n    public int getLargestMainSize() {\n        if (mFlexLines.size() == 0) {\n            return 0;\n        }\n        int largestSize = Integer.MIN_VALUE;\n        for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n            FlexLine flexLine = mFlexLines.get(i);\n            largestSize = Math.max(largestSize, flexLine.mMainSize);\n        }\n        return largestSize;\n    }\n\n    @Override\n    public int getSumOfCrossSize() {\n        int sum = 0;\n        for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n            FlexLine flexLine = mFlexLines.get(i);\n            // TODO: Consider adding decorator between flex lines.\n            sum += flexLine.mCrossSize;\n        }\n        return sum;\n    }\n\n    @Override\n    public void setFlexLines(List<FlexLine> flexLines) {\n        mFlexLines = flexLines;\n    }\n\n    @Override\n    public List<FlexLine> getFlexLinesInternal() {\n        return mFlexLines;\n    }\n\n    @Override\n    public void updateViewCache(int position, View view) {\n        mViewCache.put(position, view);\n    }\n    // The end of methods from FlexContainer\n\n    // ScrollVectorProvider method\n    @Override\n    public PointF computeScrollVectorForPosition(int targetPosition) {\n        if (getChildCount() == 0) {\n            return null;\n        }\n        View view = getChildAt(0);\n        if (view == null) {\n            return null;\n        }\n        int firstChildPos = getPosition(view);\n        int direction = targetPosition < firstChildPos ? -1 : 1;\n        if (isMainAxisDirectionHorizontal()) {\n            return new PointF(0, direction);\n        } else {\n            return new PointF(direction, 0);\n        }\n    }\n\n    @Override\n    public RecyclerView.LayoutParams generateDefaultLayoutParams() {\n        return new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);\n    }\n\n    @Override\n    public RecyclerView.LayoutParams generateLayoutParams(Context c, AttributeSet attrs) {\n        return new LayoutParams(c, attrs);\n    }\n\n    @Override\n    public boolean checkLayoutParams(RecyclerView.LayoutParams lp) {\n        return lp instanceof LayoutParams;\n    }\n\n    @Override\n    public void onAdapterChanged(RecyclerView.Adapter oldAdapter, RecyclerView.Adapter newAdapter) {\n        removeAllViews();\n    }\n\n    @Override\n    public Parcelable onSaveInstanceState() {\n        if (mPendingSavedState != null) {\n            return new SavedState(mPendingSavedState);\n        }\n        SavedState savedState = new SavedState();\n        if (getChildCount() > 0) {\n            // TODO: Find the child from end if mFlexWrap == FlexWrap.WRAP_REVERSE\n            View firstView = getChildClosestToStart();\n            savedState.mAnchorPosition = getPosition(firstView);\n            savedState.mAnchorOffset = mOrientationHelper.getDecoratedStart(firstView) -\n                    mOrientationHelper.getStartAfterPadding();\n        } else {\n            savedState.invalidateAnchor();\n        }\n        return savedState;\n    }\n\n    @Override\n    public void onRestoreInstanceState(Parcelable state) {\n        if (state instanceof SavedState) {\n            mPendingSavedState = (SavedState) state;\n            requestLayout();\n            if (DEBUG) {\n                Log.d(TAG, \"Loaded saved state. \" + mPendingSavedState);\n            }\n        } else {\n            if (DEBUG) {\n                Log.w(TAG, \"Invalid state was trying to be restored. \" + state);\n            }\n        }\n    }\n\n    @Override\n    public void onItemsAdded(@NonNull RecyclerView recyclerView, int positionStart, int itemCount) {\n        super.onItemsAdded(recyclerView, positionStart, itemCount);\n        updateDirtyPosition(positionStart);\n    }\n\n    @Override\n    public void onItemsUpdated(@NonNull RecyclerView recyclerView, int positionStart, int itemCount,\n            Object payload) {\n        super.onItemsUpdated(recyclerView, positionStart, itemCount, payload);\n        updateDirtyPosition(positionStart);\n    }\n\n    @Override\n    public void onItemsUpdated(@NonNull RecyclerView recyclerView, int positionStart, int itemCount) {\n        super.onItemsUpdated(recyclerView, positionStart, itemCount);\n        updateDirtyPosition(positionStart);\n    }\n\n    @Override\n    public void onItemsRemoved(@NonNull RecyclerView recyclerView, int positionStart, int itemCount) {\n        super.onItemsRemoved(recyclerView, positionStart, itemCount);\n        updateDirtyPosition(positionStart);\n    }\n\n    @Override\n    public void onItemsMoved(@NonNull RecyclerView recyclerView, int from, int to, int itemCount) {\n        super.onItemsMoved(recyclerView, from, to, itemCount);\n        updateDirtyPosition(Math.min(from, to));\n    }\n\n    private void updateDirtyPosition(int positionStart) {\n        int lastVisiblePosition = findLastVisibleItemPosition();\n        if (positionStart >= lastVisiblePosition) {\n            return;\n        }\n        int childCount = getChildCount();\n        mFlexboxHelper.ensureMeasureSpecCache(childCount);\n        mFlexboxHelper.ensureMeasuredSizeCache(childCount);\n        mFlexboxHelper.ensureIndexToFlexLine(childCount);\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n\n        if (positionStart >= mFlexboxHelper.mIndexToFlexLine.length) {\n            return;\n        }\n\n        mDirtyPosition = positionStart;\n\n        View firstView = getChildClosestToStart();\n        if (firstView == null) {\n            return;\n        }\n\n        // Assign the pending scroll position and offset so that the first visible position is\n        // restored in the next layout.\n        mPendingScrollPosition = getPosition(firstView);\n\n        if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n            mPendingScrollPositionOffset = mOrientationHelper.getDecoratedEnd(firstView) +\n                    mOrientationHelper.getEndPadding();\n        } else {\n            mPendingScrollPositionOffset = mOrientationHelper.getDecoratedStart(firstView) -\n                    mOrientationHelper.getStartAfterPadding();\n        }\n    }\n\n    @Override\n    public void onLayoutChildren(RecyclerView.Recycler recycler, RecyclerView.State state) {\n        // Layout algorithm:\n        // 1) Find an anchor coordinate and anchor flex line position. If not found, the coordinate\n        //    starts from zero.\n        // 2) From the anchor position to the visible area, calculate the flex lines that needs to\n        //    be filled.\n        // 3) Fill toward end from the anchor position\n        // 4) Fill toward start from the anchor position\n        if (DEBUG) {\n            Log.d(TAG, \"onLayoutChildren started\");\n            Log.d(TAG, \"getChildCount: \" + getChildCount());\n            Log.d(TAG, \"State: \" + state);\n            Log.d(TAG, \"PendingSavedState: \" + mPendingSavedState);\n            Log.d(TAG, \"PendingScrollPosition: \" + mPendingScrollPosition);\n            Log.d(TAG, \"PendingScrollOffset: \" + mPendingScrollPositionOffset);\n        }\n\n        // Assign the Recycler and the State as the member variables so that\n        // the method from FlexContainer (such as getFlexItemCount()) returns the number of\n        // flex items from the adapter not the child count in the LayoutManager because\n        // LayoutManager#getChildCount doesn't include the views that are detached or scrapped.\n        mRecycler = recycler;\n        mState = state;\n        int childCount = state.getItemCount();\n        if (childCount == 0 && state.isPreLayout()) {\n            return;\n        }\n        resolveLayoutDirection();\n        ensureOrientationHelper();\n        ensureLayoutState();\n        mFlexboxHelper.ensureMeasureSpecCache(childCount);\n        mFlexboxHelper.ensureMeasuredSizeCache(childCount);\n\n        mFlexboxHelper.ensureIndexToFlexLine(childCount);\n\n        mLayoutState.mShouldRecycle = false;\n\n        if (mPendingSavedState != null && mPendingSavedState.hasValidAnchor(childCount)) {\n            mPendingScrollPosition = mPendingSavedState.mAnchorPosition;\n        }\n\n        if (!mAnchorInfo.mValid || mPendingScrollPosition != NO_POSITION ||\n                mPendingSavedState != null) {\n            mAnchorInfo.reset();\n            updateAnchorInfoForLayout(state, mAnchorInfo);\n            mAnchorInfo.mValid = true;\n        }\n        detachAndScrapAttachedViews(recycler);\n\n        if (mAnchorInfo.mLayoutFromEnd) {\n            updateLayoutStateToFillStart(mAnchorInfo, false, true);\n        } else {\n            updateLayoutStateToFillEnd(mAnchorInfo, false, true);\n        }\n        if (DEBUG) {\n            Log.d(TAG,\n                    String.format(\"onLayoutChildren. recycler.getScrapList.size(): %s, state: %s\",\n                            recycler.getScrapList().size(), state));\n        }\n\n        updateFlexLines(childCount);\n        if (DEBUG) {\n            for (int i = 0, size = mFlexLines.size(); i < size; i++) {\n                FlexLine flexLine = mFlexLines.get(i);\n                Log.d(TAG, String.format(\"%d flex line. MainSize: %d, CrossSize: %d, itemCount: %d\",\n                        i, flexLine.getMainSize(), flexLine.getCrossSize(),\n                        flexLine.getItemCount()));\n            }\n        }\n\n        int startOffset;\n        int endOffset;\n        int filledToEnd = fill(recycler, state, mLayoutState);\n        if (mAnchorInfo.mLayoutFromEnd) {\n            if (DEBUG) {\n                Log.d(TAG, String.format(\"filled: %d toward start\", filledToEnd));\n            }\n            startOffset = mLayoutState.mOffset;\n            updateLayoutStateToFillEnd(mAnchorInfo, true, false);\n            int filledToStart = fill(recycler, state, mLayoutState);\n            if (DEBUG) {\n                Log.d(TAG, String.format(\"filled: %d toward end\", filledToStart));\n            }\n            endOffset = mLayoutState.mOffset;\n        } else {\n            if (DEBUG) {\n                Log.d(TAG, String.format(\"filled: %d toward end\", filledToEnd));\n            }\n            endOffset = mLayoutState.mOffset;\n            updateLayoutStateToFillStart(mAnchorInfo, true, false);\n            int filledToStart = fill(recycler, state, mLayoutState);\n            if (DEBUG) {\n                Log.d(TAG, String.format(\"filled: %d toward start\", filledToStart));\n            }\n            startOffset = mLayoutState.mOffset;\n        }\n\n        if (getChildCount() > 0) {\n            if (mAnchorInfo.mLayoutFromEnd) {\n                int fixOffset = fixLayoutEndGap(endOffset, recycler, state, true);\n                startOffset += fixOffset;\n                fixLayoutStartGap(startOffset, recycler, state, false);\n            } else {\n                int fixOffset = fixLayoutStartGap(startOffset, recycler, state, true);\n                endOffset += fixOffset;\n                fixLayoutEndGap(endOffset, recycler, state, false);\n            }\n        }\n    }\n\n    /**\n     * Fill the gap the toward the start position if the gap to be filled is made.\n     * Large part is copied from LinearLayoutManager#fixLayoutStartGap.\n     */\n    private int fixLayoutStartGap(int startOffset, RecyclerView.Recycler recycler,\n            RecyclerView.State state, boolean canOffsetChildren) {\n        int gap;\n        int fixOffset;\n        if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n            gap = mOrientationHelper.getEndAfterPadding() - startOffset;\n            if (gap > 0) {\n                // check if we should fix this gap.\n                fixOffset = handleScrollingMainOrientation(-gap, recycler, state);\n            } else {\n                return 0; // nothing to fix\n            }\n        } else {\n            gap = startOffset - mOrientationHelper.getStartAfterPadding();\n            if (gap > 0) {\n                // check if we should fix this gap.\n                fixOffset = -handleScrollingMainOrientation(gap, recycler, state);\n            } else {\n                return 0; // nothing to fix\n            }\n        }\n        startOffset += fixOffset;\n        if (canOffsetChildren) {\n            // re-calculate gap, see if we could fix it\n            gap = startOffset - mOrientationHelper.getStartAfterPadding();\n            if (gap > 0) {\n                mOrientationHelper.offsetChildren(-gap);\n                return fixOffset - gap;\n            }\n        }\n        return fixOffset;\n    }\n\n    /**\n     * Fill the gap the toward the end position if the gap to be filled is made.\n     * This process is necessary in a case like {@link #scrollToPosition(int)} is called\n     * for the last item, otherwise the last item is placed as the first line.\n     * Large part is copied from LinearLayoutManager#fixLayoutEndGap.\n     */\n    private int fixLayoutEndGap(int endOffset, RecyclerView.Recycler recycler,\n            RecyclerView.State state, boolean canOffsetChildren) {\n        int gap;\n        boolean columnAndRtl = !isMainAxisDirectionHorizontal() && mIsRtl;\n        int fixOffset;\n        if (columnAndRtl) {\n            gap = endOffset - mOrientationHelper.getStartAfterPadding();\n            if (gap > 0) {\n                fixOffset = handleScrollingMainOrientation(gap, recycler, state);\n            } else {\n                return 0; // nothing to fix\n            }\n        } else {\n            gap = mOrientationHelper.getEndAfterPadding() - endOffset;\n            if (gap > 0) {\n                fixOffset = -handleScrollingMainOrientation(-gap, recycler, state);\n            } else {\n                return 0; // nothing to fix\n            }\n        }\n\n        // move offset according to scroll amount\n        endOffset += fixOffset;\n        if (canOffsetChildren) {\n            // re-calculate gap, see if we could fix it\n            gap = mOrientationHelper.getEndAfterPadding() - endOffset;\n            if (gap > 0) {\n                mOrientationHelper.offsetChildren(gap);\n                return gap + fixOffset;\n            }\n        }\n        return fixOffset;\n    }\n\n    private void updateFlexLines(int childCount) {\n        //noinspection ResourceType\n        int widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(getWidth(), getWidthMode());\n        //noinspection ResourceType\n        int heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(getHeight(), getHeightMode());\n        int width = getWidth();\n        int height = getHeight();\n        boolean isMainSizeChanged;\n        int needsToFill;\n        // Clear the flex lines if the main size has changed from the last measurement.\n        // For example this happens when the developer handles the configuration changes manually\n        // or the user change the width boundary in the multi window mode.\n        if (isMainAxisDirectionHorizontal()) {\n            isMainSizeChanged = mLastWidth != Integer.MIN_VALUE && mLastWidth != width;\n\n            // If the mInfinite flag is set to true (that usually happens when RecyclerViews are\n            // nested and inner RecyclerView's layout_height is set to wrap_content, thus height is\n            // passed as 0 from the RecyclerView)\n            // Set the upper limit as the height of the device in order to prevent computing all\n            // items in the adapter\n            needsToFill = mLayoutState.mInfinite ?\n                    mContext.getResources().getDisplayMetrics().heightPixels\n                    : mLayoutState.mAvailable;\n        } else {\n            isMainSizeChanged = mLastHeight != Integer.MIN_VALUE && mLastHeight != height;\n\n            // If the mInfinite flag is set to true (that usually happens when RecyclerViews are\n            // nested and inner RecyclerView's layout_width is set to wrap_content, thus width is\n            // passed as 0 from the RecyclerView)\n            // Set the upper limit as the width of the device in order to prevent computing all\n            // items in the adapter\n            needsToFill = mLayoutState.mInfinite ?\n                    mContext.getResources().getDisplayMetrics().widthPixels\n                    : mLayoutState.mAvailable;\n        }\n\n        mLastWidth = width;\n        mLastHeight = height;\n\n        if (mDirtyPosition == NO_POSITION &&\n                (mPendingScrollPosition != NO_POSITION || isMainSizeChanged)) {\n            if (mAnchorInfo.mLayoutFromEnd) {\n                // Prior flex lines should be already calculated, don't have to be updated\n                return;\n            }\n            // TODO: This path may need another consideration to not calculate the entire flex\n            // lines prior to the anchor position since it may cause noticeable amount of\n            // skipped frames.\n            // Another note: deciding anchor position for the anchor view assumes that prior\n            // flex lines are calculated otherwise the position of the view can't be decided.\n            // It may be possible that assumes the anchor view is always at the start of a flex\n            // line and calculate the rest of flex lines as user scrolls to the top (toward the\n            // start) incrementally, but that approach may lead to inconsistent anchor view\n            // position\n            mFlexLines.clear();\n            assert mFlexboxHelper.mIndexToFlexLine != null;\n            mFlexLinesResult.reset();\n            if (isMainAxisDirectionHorizontal()) {\n                mFlexboxHelper\n                        .calculateHorizontalFlexLinesToIndex(mFlexLinesResult,\n                                widthMeasureSpec, heightMeasureSpec,\n                                needsToFill, mAnchorInfo.mPosition, mFlexLines);\n            } else {\n                mFlexboxHelper\n                        .calculateVerticalFlexLinesToIndex(mFlexLinesResult,\n                                widthMeasureSpec, heightMeasureSpec,\n                                needsToFill, mAnchorInfo.mPosition, mFlexLines);\n            }\n            mFlexLines = mFlexLinesResult.mFlexLines;\n            mFlexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec);\n            mFlexboxHelper.stretchViews();\n            mAnchorInfo.mFlexLinePosition =\n                    mFlexboxHelper.mIndexToFlexLine[mAnchorInfo.mPosition];\n            mLayoutState.mFlexLinePosition = mAnchorInfo.mFlexLinePosition;\n        } else {\n            // Calculate the flex lines until the calculated cross size reaches the\n            // LayoutState#mAvailable (or until the end of the flex container)\n            // calculation can be done incrementally because the flex lines prior to the anchor\n            // position haven't changed\n            int fromIndex = mDirtyPosition != NO_POSITION ?\n                    Math.min(mDirtyPosition, mAnchorInfo.mPosition) : mAnchorInfo.mPosition;\n\n            mFlexLinesResult.reset();\n            if (isMainAxisDirectionHorizontal()) {\n                if (mFlexLines.size() > 0) {\n                    // Remove the already calculated flex lines from the fromIndex (either of\n                    // anchor position or the position marked as dirty (last time the item was\n                    // changed) and calculate beyond the available amount\n                    // (visible area that needs to be filled)\n                    mFlexboxHelper.clearFlexLines(mFlexLines, fromIndex);\n                    mFlexboxHelper.calculateFlexLines(mFlexLinesResult, widthMeasureSpec,\n                            heightMeasureSpec, needsToFill, fromIndex, mAnchorInfo.mPosition,\n                            mFlexLines);\n                } else {\n                    mFlexboxHelper.ensureIndexToFlexLine(childCount);\n                    mFlexboxHelper\n                            .calculateHorizontalFlexLines(mFlexLinesResult,\n                                    widthMeasureSpec, heightMeasureSpec,\n                                    needsToFill, 0, mFlexLines);\n                }\n            } else {\n                if (mFlexLines.size() > 0) {\n                    // Remove the already calculated flex lines from the fromIndex (either of\n                    // anchor position or the position marked as dirty (last time the item was\n                    // changed) and calculate beyond the available amount\n                    // (visible area that needs to be filled)\n                    mFlexboxHelper.clearFlexLines(mFlexLines, fromIndex);\n                    mFlexboxHelper.calculateFlexLines(mFlexLinesResult, heightMeasureSpec,\n                            widthMeasureSpec, needsToFill, fromIndex, mAnchorInfo.mPosition,\n                            mFlexLines);\n                } else {\n                    mFlexboxHelper.ensureIndexToFlexLine(childCount);\n                    mFlexboxHelper\n                            .calculateVerticalFlexLines(mFlexLinesResult, widthMeasureSpec,\n                                    heightMeasureSpec, needsToFill, 0, mFlexLines);\n                }\n            }\n            mFlexLines = mFlexLinesResult.mFlexLines;\n            mFlexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec,\n                    fromIndex);\n            // Unlike the FlexboxLayout not calling FlexboxHelper#determineCrossSize because\n            // the align content attribute (which is used to determine the cross size) is only\n            // effective\n            // when the size of flex line is equal or more than 2 and the parent height\n            // (length along the cross size) is fixed. But in RecyclerView, these two conditions\n            // can't\n            // be true at the same time. Because it's scrollable along the cross axis\n            // or even if not (when flex wrap is \"nowrap\") the size of the flex lines should be 1.\n            mFlexboxHelper.stretchViews(fromIndex);\n        }\n    }\n\n    @Override\n    public void onLayoutCompleted(RecyclerView.State state) {\n        super.onLayoutCompleted(state);\n        if (DEBUG) {\n            Log.d(TAG, \"onLayoutCompleted. \" + state);\n        }\n        mPendingSavedState = null;\n        mPendingScrollPosition = NO_POSITION;\n        mPendingScrollPositionOffset = INVALID_OFFSET;\n        mDirtyPosition = NO_POSITION;\n        mAnchorInfo.reset();\n        mViewCache.clear();\n    }\n\n    boolean isLayoutRtl() {\n        return mIsRtl;\n    }\n\n    private void resolveLayoutDirection() {\n        int layoutDirection = getLayoutDirection();\n        switch (mFlexDirection) {\n            case FlexDirection.ROW:\n                mIsRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                mFromBottomToTop = mFlexWrap == FlexWrap.WRAP_REVERSE;\n                break;\n            case FlexDirection.ROW_REVERSE:\n                mIsRtl = layoutDirection != ViewCompat.LAYOUT_DIRECTION_RTL;\n                mFromBottomToTop = mFlexWrap == FlexWrap.WRAP_REVERSE;\n                break;\n            case FlexDirection.COLUMN:\n                mIsRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    mIsRtl = !mIsRtl;\n                }\n                mFromBottomToTop = false;\n                break;\n            case FlexDirection.COLUMN_REVERSE:\n                mIsRtl = layoutDirection == ViewCompat.LAYOUT_DIRECTION_RTL;\n                if (mFlexWrap == FlexWrap.WRAP_REVERSE) {\n                    mIsRtl = !mIsRtl;\n                }\n                mFromBottomToTop = true;\n                break;\n            default:\n                mIsRtl = false;\n                mFromBottomToTop = false;\n        }\n    }\n\n    private void updateAnchorInfoForLayout(RecyclerView.State state, AnchorInfo anchorInfo) {\n        if (updateAnchorFromPendingState(state, anchorInfo, mPendingSavedState)) {\n            if (DEBUG) {\n                Log.d(TAG, \"updated anchor from the pending state\");\n            }\n            return;\n        }\n        if (updateAnchorFromChildren(state, anchorInfo)) {\n            if (DEBUG) {\n                Log.d(TAG,\n                        String.format(\"updated anchor info from existing children. AnchorInfo: %s\",\n                                anchorInfo));\n            }\n            return;\n        }\n        if (DEBUG) {\n            Log.d(TAG, \"deciding anchor info for fresh state\");\n        }\n        anchorInfo.assignCoordinateFromPadding();\n        anchorInfo.mPosition = 0;\n        anchorInfo.mFlexLinePosition = 0;\n    }\n\n    private boolean updateAnchorFromPendingState(RecyclerView.State state, AnchorInfo anchorInfo,\n            SavedState savedState) {\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        if (state.isPreLayout() || mPendingScrollPosition == NO_POSITION) {\n            return false;\n        }\n        if (mPendingScrollPosition < 0 || mPendingScrollPosition >= state.getItemCount()) {\n            mPendingScrollPosition = NO_POSITION;\n            mPendingScrollPositionOffset = INVALID_OFFSET;\n            if (DEBUG) {\n                Log.e(TAG, \"ignoring invalid scroll position \" + mPendingScrollPosition);\n            }\n            return false;\n        }\n\n        anchorInfo.mPosition = mPendingScrollPosition;\n        anchorInfo.mFlexLinePosition = mFlexboxHelper.mIndexToFlexLine[anchorInfo.mPosition];\n        if (mPendingSavedState != null && mPendingSavedState.hasValidAnchor(state.getItemCount())) {\n            anchorInfo.mCoordinate = mOrientationHelper.getStartAfterPadding() +\n                    savedState.mAnchorOffset;\n            anchorInfo.mAssignedFromSavedState = true;\n            anchorInfo.mFlexLinePosition = NO_POSITION;\n            return true;\n        }\n\n        if (mPendingScrollPositionOffset == INVALID_OFFSET) {\n            View anchorView = findViewByPosition(mPendingScrollPosition);\n            if (anchorView != null) {\n                if (mOrientationHelper.getDecoratedMeasurement(anchorView) >\n                        mOrientationHelper.getTotalSpace()) {\n                    anchorInfo.assignCoordinateFromPadding();\n                    return true;\n                }\n                int startGap = mOrientationHelper.getDecoratedStart(anchorView)\n                        - mOrientationHelper.getStartAfterPadding();\n                if (startGap < 0) {\n                    anchorInfo.mCoordinate = mOrientationHelper.getStartAfterPadding();\n                    anchorInfo.mLayoutFromEnd = false;\n                    return true;\n                }\n\n                int endGap = mOrientationHelper.getEndAfterPadding() -\n                        mOrientationHelper.getDecoratedEnd(anchorView);\n                if (endGap < 0) {\n                    anchorInfo.mCoordinate = mOrientationHelper.getEndAfterPadding();\n                    anchorInfo.mLayoutFromEnd = true;\n                    return true;\n                }\n                anchorInfo.mCoordinate = anchorInfo.mLayoutFromEnd ?\n                        (mOrientationHelper.getDecoratedEnd(anchorView) +\n                                mOrientationHelper.getTotalSpaceChange())\n                        : mOrientationHelper.getDecoratedStart(anchorView);\n            } else {\n                if (getChildCount() > 0) {\n                    View view = getChildAt(0);\n                    if (view != null) {\n                        int position = getPosition(view);\n                        anchorInfo.mLayoutFromEnd = mPendingScrollPosition < position;\n                    }\n                }\n                anchorInfo.assignCoordinateFromPadding();\n            }\n            return true;\n        }\n\n        // TODO: Support reverse layout when flex wrap == FlexWrap.WRAP_REVERSE\n        if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n            anchorInfo.mCoordinate = mPendingScrollPositionOffset\n                    - mOrientationHelper.getEndPadding();\n        } else {\n            anchorInfo.mCoordinate = mOrientationHelper.getStartAfterPadding()\n                    + mPendingScrollPositionOffset;\n        }\n        return true;\n    }\n\n    /**\n     * Finds an anchor child from existing Views. Most of the time, this is the view closest to\n     * start or end that has a valid position (e.g. not removed).\n     * Large part refers to the same method from LinearLayout#updateAnchorFromChildren\n     */\n    private boolean updateAnchorFromChildren(RecyclerView.State state, AnchorInfo anchorInfo) {\n        if (getChildCount() == 0) {\n            return false;\n        }\n        // TODO: Consider the focused view\n\n        View referenceChild = anchorInfo.mLayoutFromEnd\n                ? findLastReferenceChild(state.getItemCount())\n                : findFirstReferenceChild(state.getItemCount());\n        if (referenceChild != null) {\n            anchorInfo.assignFromView(referenceChild);\n            // If all visible views are removed in 1 pass, reference child might be out of bounds.\n            // If that is the case, offset it back to 0 so that we use these pre-layout children.\n            if (!state.isPreLayout() && supportsPredictiveItemAnimations()) {\n                // validate this child is at least partially visible. if not, offset it to start\n                final boolean notVisible =\n                        mOrientationHelper.getDecoratedStart(referenceChild) >= mOrientationHelper\n                                .getEndAfterPadding()\n                                || mOrientationHelper.getDecoratedEnd(referenceChild)\n                                < mOrientationHelper.getStartAfterPadding();\n                if (notVisible) {\n                    anchorInfo.mCoordinate = anchorInfo.mLayoutFromEnd\n                            ? mOrientationHelper.getEndAfterPadding()\n                            : mOrientationHelper.getStartAfterPadding();\n                }\n            }\n            return true;\n        }\n        return false;\n    }\n\n    /**\n     * Find the reference view to be used as an anchor. It tries to find the view who has the\n     * maximum/minimum start/end (differs depending on if the container if RTL and the main axis\n     * direction) coordinate in the first visible flex line.\n     *\n     * @param itemCount the number of the items in this layout including invisible items\n     * @return the reference view\n     */\n    private View findFirstReferenceChild(int itemCount) {\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        View firstFound = findReferenceChild(0, getChildCount(), itemCount);\n        if (firstFound == null) {\n            return null;\n        }\n        int firstFoundPosition = getPosition(firstFound);\n        int firstFoundLinePosition = mFlexboxHelper.mIndexToFlexLine[firstFoundPosition];\n        if (firstFoundLinePosition == NO_POSITION) {\n            return null;\n        }\n        FlexLine firstFoundLine = mFlexLines.get(firstFoundLinePosition);\n        return findFirstReferenceViewInLine(firstFound, firstFoundLine);\n    }\n\n    /**\n     * Find the reference view to be used as an anchor. It tries to find the view who has the\n     * maximum/minimum start/end (differs depending on if the container if RTL and the main axis\n     * direction) coordinate in the last visible flex line.\n     *\n     * @param itemCount the number of the items in this layout including invisible items\n     * @return the reference view\n     */\n    private View findLastReferenceChild(int itemCount) {\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        View lastFound = findReferenceChild(getChildCount() - 1, -1, itemCount);\n        if (lastFound == null) {\n            return null;\n        }\n        int lastFoundPosition = getPosition(lastFound);\n        int lastFoundLinePosition = mFlexboxHelper.mIndexToFlexLine[lastFoundPosition];\n        FlexLine lastFoundLine = mFlexLines.get(lastFoundLinePosition);\n        return findLastReferenceViewInLine(lastFound, lastFoundLine);\n    }\n\n    /**\n     * Find a visible (or less preferred invisible) view within the given start and end index.\n     * Large part refers to the same method in LinearLayoutManager#findReferenceChild\n     *\n     * @param start     the start index within the range to find a view\n     * @param end       the end index within the range to find a view\n     * @param itemCount the item count\n     * @return the found view within the range of the given start and\n     */\n    private View findReferenceChild(int start, int end, int itemCount) {\n        ensureOrientationHelper();\n        ensureLayoutState();\n        View invalidMatch = null;\n        View outOfBoundsMatch = null;\n        int boundStart = mOrientationHelper.getStartAfterPadding();\n        int boundEnd = mOrientationHelper.getEndAfterPadding();\n        int diff = end > start ? 1 : -1;\n        for (int i = start; i != end; i += diff) {\n            View view = getChildAt(i);\n            if (view == null) {\n                continue;\n            }\n            int position = getPosition(view);\n            if (position >= 0 && position < itemCount) {\n                if (((RecyclerView.LayoutParams) view.getLayoutParams()).isItemRemoved()) {\n                    if (invalidMatch == null) {\n                        invalidMatch = view;\n                    }\n                } else if (mOrientationHelper.getDecoratedStart(view) < boundStart ||\n                        mOrientationHelper.getDecoratedEnd(view) > boundEnd) {\n                    if (outOfBoundsMatch == null) {\n                        outOfBoundsMatch = view;\n                    }\n                } else {\n                    return view;\n                }\n            }\n        }\n        return outOfBoundsMatch != null ? outOfBoundsMatch : invalidMatch;\n    }\n\n    private View getChildClosestToStart() {\n        // TODO: Find from end when mFlexWrap == FlexWrap.WRAP_REVERSE\n        return getChildAt(0);\n    }\n\n    /**\n     * Fills the remaining space defined by the layoutState on\n     * how many pixels should be filled (defined by {@link LayoutState#mAvailable}.\n     * The large part refers to the LinearLayoutManager#fill method except for the fill direction.\n     * Because FlexboxLayoutManager needs to care two scrolling directions:\n     * <li>\n     * <ul>Along the cross axis - When flex wrap is set to either FlexWrap.WRAP or\n     * FlexWrap.WRAP_REVERSE, the layout needs to scroll along the cross axis.</ul>\n     * <ul>Along the main axis - When flex wrap is set t FlexWrap.NOWRAP, the layout needs\n     * to scroll along the main axis if there are overflowing flex items.</ul>\n     * </li>\n     *\n     * @return the amount of pixels filled\n     */\n    private int fill(RecyclerView.Recycler recycler, RecyclerView.State state,\n            LayoutState layoutState) {\n        if (layoutState.mScrollingOffset != LayoutState.SCROLLING_OFFSET_NaN) {\n            if (layoutState.mAvailable < 0) {\n                layoutState.mScrollingOffset += layoutState.mAvailable;\n            }\n            recycleByLayoutState(recycler, layoutState);\n        }\n        int start = layoutState.mAvailable;\n        int remainingSpace = layoutState.mAvailable;\n        int consumed = 0;\n        boolean mainAxisHorizontal = isMainAxisDirectionHorizontal();\n        while ((remainingSpace > 0 || mLayoutState.mInfinite) &&\n                layoutState.hasMore(state, mFlexLines)) {\n            FlexLine flexLine = mFlexLines.get(layoutState.mFlexLinePosition);\n            layoutState.mPosition = flexLine.mFirstIndex;\n            consumed += layoutFlexLine(flexLine, layoutState);\n\n            if (!mainAxisHorizontal && mIsRtl) {\n                layoutState.mOffset -= flexLine.getCrossSize() * layoutState.mLayoutDirection;\n            } else {\n                layoutState.mOffset += flexLine.getCrossSize() * layoutState.mLayoutDirection;\n            }\n\n            remainingSpace -= flexLine.getCrossSize();\n        }\n        layoutState.mAvailable -= consumed;\n        if (layoutState.mScrollingOffset != LayoutState.SCROLLING_OFFSET_NaN) {\n            layoutState.mScrollingOffset += consumed;\n            if (layoutState.mAvailable < 0) {\n                layoutState.mScrollingOffset += layoutState.mAvailable;\n            }\n            recycleByLayoutState(recycler, layoutState);\n        }\n        return start - layoutState.mAvailable;\n    }\n\n    private void recycleByLayoutState(RecyclerView.Recycler recycler, LayoutState layoutState) {\n        if (!layoutState.mShouldRecycle) {\n            return;\n        }\n        if (layoutState.mLayoutDirection == LayoutState.LAYOUT_START) {\n            // TODO: Consider the case mFlexWrap is set to nowrap and view is recycled individually\n            recycleFlexLinesFromEnd(recycler, layoutState);\n        } else {\n            recycleFlexLinesFromStart(recycler, layoutState);\n        }\n    }\n\n    private void recycleFlexLinesFromStart(RecyclerView.Recycler recycler,\n            LayoutState layoutState) {\n        if (layoutState.mScrollingOffset < 0) {\n            return;\n        }\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        int childCount = getChildCount();\n        if (childCount == 0) {\n            return;\n        }\n        View firstView = getChildAt(0);\n        if (firstView == null) {\n            return;\n        }\n        int currentLineIndex = mFlexboxHelper.mIndexToFlexLine[getPosition(firstView)];\n        if (currentLineIndex == NO_POSITION) {\n            return;\n        }\n        FlexLine flexLine = mFlexLines.get(currentLineIndex);\n        int recycleTo = -1;\n        for (int i = 0; i < childCount; i++) {\n            View view = getChildAt(i);\n            if (view == null) {\n                continue;\n            }\n            if (canViewBeRecycledFromStart(view, layoutState.mScrollingOffset)) {\n                if (flexLine.mLastIndex == getPosition(view)) {\n                    // Recycle the views in a flex line if all views end positions are lower than\n                    // the scrolling offset because the views are laid out as a flex line unit.\n                    // We need to also recycle the views as an unit of a flex line\n                    recycleTo = i;\n                    if (currentLineIndex >= mFlexLines.size() - 1) {\n                        // Reached to the last line\n                        break;\n                    } else {\n                        currentLineIndex += layoutState.mLayoutDirection;\n                        flexLine = mFlexLines.get(currentLineIndex);\n                    }\n                }\n            } else {\n                break;\n            }\n        }\n        recycleChildren(recycler, 0, recycleTo);\n    }\n\n    private boolean canViewBeRecycledFromStart(View view, int scrollingOffset) {\n        if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n            return mOrientationHelper.getEnd() -\n                    mOrientationHelper.getDecoratedStart(view) <= scrollingOffset;\n        } else {\n            return mOrientationHelper.getDecoratedEnd(view) <= scrollingOffset;\n        }\n    }\n\n    private void recycleFlexLinesFromEnd(RecyclerView.Recycler recycler, LayoutState layoutState) {\n        if (layoutState.mScrollingOffset < 0) {\n            return;\n        }\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        int childCount = getChildCount();\n        if (childCount == 0) {\n            return;\n        }\n\n        View lastView = getChildAt(childCount - 1);\n        if (lastView == null) {\n            return;\n        }\n        int currentLineIndex = mFlexboxHelper.mIndexToFlexLine[getPosition(lastView)];\n        if (currentLineIndex == NO_POSITION) {\n            return;\n        }\n        int recycleTo = childCount - 1;\n        int recycleFrom = childCount;\n        FlexLine flexLine = mFlexLines.get(currentLineIndex);\n        for (int i = childCount - 1; i >= 0; i--) {\n            View view = getChildAt(i);\n            if (view == null) {\n                continue;\n            }\n            if (canViewBeRecycledFromEnd(view, layoutState.mScrollingOffset)) {\n                if (flexLine.mFirstIndex == getPosition(view)) {\n                    // Recycle the views in a flex line if all views start positions are beyond the\n                    // limit because the views are laid out as a flex line unit. We need to also\n                    // recycle the views as an unit of a flex line\n                    recycleFrom = i;\n                    if (currentLineIndex <= 0) {\n                        // Reached to the first flex line\n                        break;\n                    } else {\n                        currentLineIndex += layoutState.mLayoutDirection;\n                        flexLine = mFlexLines.get(currentLineIndex);\n                    }\n                }\n            } else {\n                break;\n            }\n        }\n        recycleChildren(recycler, recycleFrom, recycleTo);\n    }\n\n    private boolean canViewBeRecycledFromEnd(View view, int scrollingOffset) {\n        if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n            return mOrientationHelper.getDecoratedEnd(view) <= scrollingOffset;\n        } else {\n            return mOrientationHelper.getDecoratedStart(view) >=\n                    mOrientationHelper.getEnd() - scrollingOffset;\n        }\n    }\n\n    /**\n     * Recycles children between given indices.\n     *\n     * @param startIndex inclusive\n     * @param endIndex   inclusive\n     */\n    private void recycleChildren(RecyclerView.Recycler recycler, int startIndex, int endIndex) {\n        for (int i = endIndex; i >= startIndex; i--) {\n            removeAndRecycleViewAt(i, recycler);\n        }\n    }\n\n    private int layoutFlexLine(FlexLine flexLine, LayoutState layoutState) {\n        if (isMainAxisDirectionHorizontal()) {\n            return layoutFlexLineMainAxisHorizontal(flexLine, layoutState);\n        } else {\n            return layoutFlexLineMainAxisVertical(flexLine, layoutState);\n        }\n    }\n\n    private int layoutFlexLineMainAxisHorizontal(FlexLine flexLine, LayoutState layoutState) {\n        assert mFlexboxHelper.mMeasureSpecCache != null;\n\n        int paddingLeft = getPaddingLeft();\n        int paddingRight = getPaddingRight();\n        int parentWidth = getWidth();\n\n        int childTop = layoutState.mOffset;\n        if (layoutState.mLayoutDirection == LayoutState.LAYOUT_START) {\n            childTop = childTop - flexLine.mCrossSize;\n        }\n        int startPosition = layoutState.mPosition;\n\n        float childLeft;\n\n        // Only used when mIsRtl is true\n        float childRight;\n        float spaceBetweenItem = 0f;\n        switch (mJustifyContent) {\n            case JustifyContent.FLEX_START:\n                childLeft = paddingLeft;\n                childRight = parentWidth - paddingRight;\n                break;\n            case JustifyContent.FLEX_END:\n                childLeft = parentWidth - flexLine.mMainSize + paddingRight;\n                childRight = flexLine.mMainSize - paddingLeft;\n                break;\n            case JustifyContent.CENTER:\n                childLeft = paddingLeft + (parentWidth - flexLine.mMainSize) / 2f;\n                childRight = parentWidth - paddingRight - (parentWidth - flexLine.mMainSize) / 2f;\n                break;\n            case JustifyContent.SPACE_AROUND:\n                if (flexLine.mItemCount != 0) {\n                    spaceBetweenItem = (parentWidth - flexLine.mMainSize)\n                            / (float) flexLine.mItemCount;\n                }\n                childLeft = paddingLeft + spaceBetweenItem / 2f;\n                childRight = parentWidth - paddingRight - spaceBetweenItem / 2f;\n                break;\n            case JustifyContent.SPACE_BETWEEN:\n                childLeft = paddingLeft;\n                float denominator = flexLine.mItemCount != 1 ? flexLine.mItemCount - 1 : 1f;\n                spaceBetweenItem = (parentWidth - flexLine.mMainSize) / denominator;\n                childRight = parentWidth - paddingRight;\n                break;\n            case JustifyContent.SPACE_EVENLY:\n                if (flexLine.mItemCount != 0) {\n                    spaceBetweenItem = (parentWidth - flexLine.mMainSize)\n                            / (float) (flexLine.mItemCount + 1);\n                }\n                childLeft = paddingLeft + spaceBetweenItem;\n                childRight = parentWidth - paddingRight - spaceBetweenItem;\n                break;\n            default:\n                throw new IllegalStateException(\n                        \"Invalid justifyContent is set: \" + mJustifyContent);\n        }\n        childLeft -= mAnchorInfo.mPerpendicularCoordinate;\n        childRight -= mAnchorInfo.mPerpendicularCoordinate;\n        spaceBetweenItem = Math.max(spaceBetweenItem, 0);\n\n        // Used only when mLayoutDirection == LayoutState.LAYOUT_START to remember the index\n        // a flex item should be inserted\n        int indexInFlexLine = 0;\n        for (int i = startPosition, itemCount = flexLine.getItemCount();\n                i < startPosition + itemCount; i++) {\n            View view = getFlexItemAt(i);\n            if (view == null) {\n                continue;\n            }\n\n            if (layoutState.mLayoutDirection == LayoutState.LAYOUT_END) {\n                calculateItemDecorationsForChild(view, TEMP_RECT);\n                addView(view);\n            } else {\n                calculateItemDecorationsForChild(view, TEMP_RECT);\n                addView(view, indexInFlexLine);\n                indexInFlexLine++;\n            }\n\n            // Retrieve the measure spec from the cache because the view may be re-created when\n            // retrieved from Recycler, in that case measured width/height are set to 0 even\n            // each visible child should be measured at least once in the FlexboxHelper\n            long measureSpec = mFlexboxHelper.mMeasureSpecCache[i];\n            int widthSpec = mFlexboxHelper.extractLowerInt(measureSpec);\n            int heightSpec = mFlexboxHelper.extractHigherInt(measureSpec);\n            LayoutParams lp = (LayoutParams) view.getLayoutParams();\n            if (shouldMeasureChild(view, widthSpec, heightSpec, lp)) {\n                view.measure(widthSpec, heightSpec);\n            }\n\n            childLeft += (lp.leftMargin + getLeftDecorationWidth(view));\n            childRight -= (lp.rightMargin + getRightDecorationWidth(view));\n\n            int topWithDecoration = childTop + getTopDecorationHeight(view);\n            if (mIsRtl) {\n                mFlexboxHelper.layoutSingleChildHorizontal(view, flexLine,\n                        Math.round(childRight) - view.getMeasuredWidth(),\n                        topWithDecoration, Math.round(childRight),\n                        topWithDecoration + view.getMeasuredHeight());\n            } else {\n                mFlexboxHelper.layoutSingleChildHorizontal(view, flexLine,\n                        Math.round(childLeft), topWithDecoration,\n                        Math.round(childLeft) + view.getMeasuredWidth(),\n                        topWithDecoration + view.getMeasuredHeight());\n            }\n            childLeft += (view.getMeasuredWidth() + lp.rightMargin + getRightDecorationWidth(view)\n                    + spaceBetweenItem);\n            childRight -= (view.getMeasuredWidth() + lp.leftMargin + getLeftDecorationWidth(view)\n                    + spaceBetweenItem);\n        }\n        layoutState.mFlexLinePosition += mLayoutState.mLayoutDirection;\n        return flexLine.getCrossSize();\n    }\n\n    private int layoutFlexLineMainAxisVertical(FlexLine flexLine, LayoutState layoutState) {\n        assert mFlexboxHelper.mMeasureSpecCache != null;\n\n        int paddingTop = getPaddingTop();\n        int paddingBottom = getPaddingBottom();\n        int parentHeight = getHeight();\n\n        int childLeft = layoutState.mOffset;\n        // childRight is used only for the layout is RTL\n        int childRight = layoutState.mOffset;\n        if (layoutState.mLayoutDirection == LayoutState.LAYOUT_START) {\n            childLeft = childLeft - flexLine.mCrossSize;\n            childRight = childRight + flexLine.mCrossSize;\n        }\n        int startPosition = layoutState.mPosition;\n\n        float childTop;\n\n        // Only used when mFromBottomToTop is true\n        float childBottom;\n        float spaceBetweenItem = 0f;\n        switch (mJustifyContent) {\n            case JustifyContent.FLEX_START:\n                childTop = paddingTop;\n                childBottom = parentHeight - paddingBottom;\n                break;\n            case JustifyContent.FLEX_END:\n                childTop = parentHeight - flexLine.mMainSize + paddingBottom;\n                childBottom = flexLine.mMainSize - paddingTop;\n                break;\n            case JustifyContent.CENTER:\n                childTop = paddingTop + (parentHeight - flexLine.mMainSize) / 2f;\n                childBottom = parentHeight - paddingBottom\n                        - (parentHeight - flexLine.mMainSize) / 2f;\n                break;\n            case JustifyContent.SPACE_AROUND:\n                if (flexLine.mItemCount != 0) {\n                    spaceBetweenItem = (parentHeight - flexLine.mMainSize)\n                            / (float) flexLine.mItemCount;\n                }\n                childTop = paddingTop + spaceBetweenItem / 2f;\n                childBottom = parentHeight - paddingBottom - spaceBetweenItem / 2f;\n                break;\n            case JustifyContent.SPACE_BETWEEN:\n                childTop = paddingTop;\n                float denominator = flexLine.mItemCount != 1 ? flexLine.mItemCount - 1 : 1f;\n                spaceBetweenItem = (parentHeight - flexLine.mMainSize) / denominator;\n                childBottom = parentHeight - paddingBottom;\n                break;\n            case JustifyContent.SPACE_EVENLY:\n                if (flexLine.mItemCount != 0) {\n                    spaceBetweenItem = (parentHeight - flexLine.mMainSize)\n                            / (float) (flexLine.mItemCount + 1);\n                }\n                childTop = paddingTop + spaceBetweenItem;\n                childBottom = parentHeight - paddingBottom - spaceBetweenItem;\n                break;\n            default:\n                throw new IllegalStateException(\n                        \"Invalid justifyContent is set: \" + mJustifyContent);\n        }\n        childTop -= mAnchorInfo.mPerpendicularCoordinate;\n        childBottom -= mAnchorInfo.mPerpendicularCoordinate;\n        spaceBetweenItem = Math.max(spaceBetweenItem, 0);\n\n        // Used only when mLayoutDirection == LayoutState.LAYOUT_START to remember the index\n        // a flex item should be inserted\n        int indexInFlexLine = 0;\n        for (int i = startPosition, itemCount = flexLine.getItemCount();\n                i < startPosition + itemCount; i++) {\n            View view = getFlexItemAt(i);\n            if (view == null) {\n                continue;\n            }\n\n            // Retrieve the measure spec from the cache because the view may be re-created when\n            // retrieved from Recycler, in that case measured width/height are set to 0 even\n            // each visible child should be measured at least once in the FlexboxHelper\n            long measureSpec = mFlexboxHelper.mMeasureSpecCache[i];\n            int widthSpec = mFlexboxHelper.extractLowerInt(measureSpec);\n            int heightSpec = mFlexboxHelper.extractHigherInt(measureSpec);\n            LayoutParams lp = (LayoutParams) view.getLayoutParams();\n            if (shouldMeasureChild(view, widthSpec, heightSpec, lp)) {\n                view.measure(widthSpec, heightSpec);\n            }\n\n            childTop += (lp.topMargin + getTopDecorationHeight(view));\n            childBottom -= (lp.rightMargin + getBottomDecorationHeight(view));\n\n            if (layoutState.mLayoutDirection == LayoutState.LAYOUT_END) {\n                calculateItemDecorationsForChild(view, TEMP_RECT);\n                addView(view);\n            } else {\n                calculateItemDecorationsForChild(view, TEMP_RECT);\n                addView(view, indexInFlexLine);\n                indexInFlexLine++;\n            }\n\n            int leftWithDecoration = childLeft + getLeftDecorationWidth(view);\n            int rightWithDecoration = childRight - getRightDecorationWidth(view);\n            if (mIsRtl) {\n                if (mFromBottomToTop) {\n                    mFlexboxHelper.layoutSingleChildVertical(view, flexLine, mIsRtl,\n                            rightWithDecoration - view.getMeasuredWidth(),\n                            Math.round(childBottom) - view.getMeasuredHeight(),\n                            rightWithDecoration, Math.round(childBottom));\n                } else {\n                    mFlexboxHelper.layoutSingleChildVertical(view, flexLine, mIsRtl,\n                            rightWithDecoration - view.getMeasuredWidth(),\n                            Math.round(childTop), rightWithDecoration,\n                            Math.round(childTop) + view.getMeasuredHeight());\n                }\n            } else {\n                if (mFromBottomToTop) {\n                    mFlexboxHelper.layoutSingleChildVertical(view, flexLine, mIsRtl,\n                            leftWithDecoration, Math.round(childBottom) - view.getMeasuredHeight(),\n                            leftWithDecoration + view.getMeasuredWidth(), Math.round(childBottom));\n                } else {\n                    mFlexboxHelper.layoutSingleChildVertical(view, flexLine, mIsRtl,\n                            leftWithDecoration, Math.round(childTop),\n                            leftWithDecoration + view.getMeasuredWidth(),\n                            Math.round(childTop) + view.getMeasuredHeight());\n                }\n            }\n            childTop += (view.getMeasuredHeight() + lp.topMargin + getBottomDecorationHeight(view)\n                    + spaceBetweenItem);\n            childBottom -= (view.getMeasuredHeight() + lp.bottomMargin +\n                    getTopDecorationHeight(view) + spaceBetweenItem);\n        }\n        layoutState.mFlexLinePosition += mLayoutState.mLayoutDirection;\n        return flexLine.getCrossSize();\n    }\n\n    @Override\n    public boolean isMainAxisDirectionHorizontal() {\n        return mFlexDirection == FlexDirection.ROW || mFlexDirection == FlexDirection.ROW_REVERSE;\n    }\n\n\n    /**\n     * Update the layout state based on the anchor information.\n     * The view holders are going to be filled toward the end position (bottom if the main axis\n     * direction is horizontal, right if the main axis direction if vertical).\n     *\n     * @param anchorInfo       the anchor information where layout should start\n     * @param fromNextLine     if set to {@code true}, layout starts from the next flex line set to\n     *                         the anchor information\n     * @param considerInfinite if set to {@code true}, the judgement if the infinite available\n     *                         space\n     *                         needs to be considered.\n     */\n    private void updateLayoutStateToFillEnd(AnchorInfo anchorInfo, boolean fromNextLine,\n            boolean considerInfinite) {\n        if (considerInfinite) {\n            resolveInfiniteAmount();\n        } else {\n            mLayoutState.mInfinite = false;\n        }\n        if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n            mLayoutState.mAvailable = anchorInfo.mCoordinate - getPaddingRight();\n        } else {\n            mLayoutState.mAvailable =\n                    mOrientationHelper.getEndAfterPadding() - anchorInfo.mCoordinate;\n        }\n        mLayoutState.mPosition = anchorInfo.mPosition;\n        mLayoutState.mItemDirection = LayoutState.ITEM_DIRECTION_TAIL;\n        mLayoutState.mLayoutDirection = LayoutState.LAYOUT_END;\n        mLayoutState.mOffset = anchorInfo.mCoordinate;\n        mLayoutState.mScrollingOffset = LayoutState.SCROLLING_OFFSET_NaN;\n        mLayoutState.mFlexLinePosition = anchorInfo.mFlexLinePosition;\n\n        if (fromNextLine\n                && mFlexLines.size() > 1\n                && anchorInfo.mFlexLinePosition >= 0\n                && anchorInfo.mFlexLinePosition < mFlexLines.size() - 1) {\n            FlexLine currentLine = mFlexLines.get(anchorInfo.mFlexLinePosition);\n            mLayoutState.mFlexLinePosition++;\n            mLayoutState.mPosition += currentLine.getItemCount();\n        }\n    }\n\n    /**\n     * Update the layout state based on the anchor information.\n     * The view holders are going to be filled toward the start position (top if the main axis\n     * direction is horizontal, left if the main axis direction if vertical).\n     *\n     * @param anchorInfo       the anchor information where layout should start\n     * @param fromPreviousLine if set to {@code true}, layout starts from the next flex line set to\n     *                         the anchor information\n     * @param considerInfinite if set to {@code true}, the judgement if the infinite available\n     *                         space\n     *                         needs to be considered.\n     */\n    private void updateLayoutStateToFillStart(AnchorInfo anchorInfo, boolean fromPreviousLine,\n            boolean considerInfinite) {\n        if (considerInfinite) {\n            resolveInfiniteAmount();\n        } else {\n            mLayoutState.mInfinite = false;\n        }\n        if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n            mLayoutState.mAvailable = mParent.getWidth() - anchorInfo.mCoordinate\n                    - mOrientationHelper.getStartAfterPadding();\n        } else {\n            mLayoutState.mAvailable = anchorInfo.mCoordinate - mOrientationHelper\n                    .getStartAfterPadding();\n        }\n        mLayoutState.mPosition = anchorInfo.mPosition;\n        mLayoutState.mItemDirection = LayoutState.ITEM_DIRECTION_TAIL;\n        mLayoutState.mLayoutDirection = LayoutState.LAYOUT_START;\n        mLayoutState.mOffset = anchorInfo.mCoordinate;\n        mLayoutState.mScrollingOffset = LayoutState.SCROLLING_OFFSET_NaN;\n        mLayoutState.mFlexLinePosition = anchorInfo.mFlexLinePosition;\n\n        if (fromPreviousLine && anchorInfo.mFlexLinePosition > 0\n                && mFlexLines.size() > anchorInfo.mFlexLinePosition) {\n            FlexLine currentLine = mFlexLines.get(anchorInfo.mFlexLinePosition);\n            mLayoutState.mFlexLinePosition--;\n            mLayoutState.mPosition -= currentLine.getItemCount();\n        }\n    }\n\n    private void resolveInfiniteAmount() {\n        int crossMode;\n        if (isMainAxisDirectionHorizontal()) {\n            crossMode = getHeightMode();\n        } else {\n            crossMode = getWidthMode();\n        }\n        // Setting the infinite flag so that the LayoutManager tries to fill the available space\n        // as much as possible. E.g. this is needed in the case RecyclerView is wrapped with another\n        // scrollable container (another RecyclerView or ScrollView) on the condition\n        // layout_height=\"wrap_content\" and flexDirection=\"row\". In such a case, the height of the\n        // inner RecyclerView (attached RecyclerView for this LayoutManager) is set to 0 at this\n        // moment, so the value of the mAvailable doesn't have enough value enough to put the\n        // already calculated flex lines.\n        mLayoutState.mInfinite =\n                crossMode == View.MeasureSpec.UNSPECIFIED || crossMode == View.MeasureSpec.AT_MOST;\n    }\n\n    private void ensureOrientationHelper() {\n        if (mOrientationHelper != null) {\n            return;\n        }\n        // There are two cases for each of main axis direction. In either case the scroll happens\n        // along the cross axis:\n        // -- Scroll vertically when mFlexWrap != FlexWrap.NOWRAP. In this case scroll happens\n        //    along the cross axis\n        //\n        // When scroll direction is vertical:\n        // -- Scroll horizontally when mFlexWrap != FlexWrap.NOWRAP. In this case scroll happens\n        //    along the cross axis\n        if (isMainAxisDirectionHorizontal()) {\n            if (mFlexWrap == FlexWrap.NOWRAP) {\n                mOrientationHelper = OrientationHelper.createHorizontalHelper(this);\n                mSubOrientationHelper = OrientationHelper.createVerticalHelper(this);\n            } else {\n                mOrientationHelper = OrientationHelper.createVerticalHelper(this);\n                mSubOrientationHelper = OrientationHelper.createHorizontalHelper(this);\n            }\n        } else {\n            if (mFlexWrap == FlexWrap.NOWRAP) {\n                mOrientationHelper = OrientationHelper.createVerticalHelper(this);\n                mSubOrientationHelper = OrientationHelper.createHorizontalHelper(this);\n            } else {\n                mOrientationHelper = OrientationHelper.createHorizontalHelper(this);\n                mSubOrientationHelper = OrientationHelper.createVerticalHelper(this);\n            }\n        }\n    }\n\n    private void ensureLayoutState() {\n        if (mLayoutState == null) {\n            mLayoutState = new LayoutState();\n        }\n    }\n\n    @Override\n    public void scrollToPosition(int position) {\n        mPendingScrollPosition = position;\n        mPendingScrollPositionOffset = INVALID_OFFSET;\n        if (mPendingSavedState != null) {\n            mPendingSavedState.invalidateAnchor();\n        }\n        requestLayout();\n    }\n\n    @Override\n    public void smoothScrollToPosition(RecyclerView recyclerView, RecyclerView.State state,\n            int position) {\n        LinearSmoothScroller smoothScroller =\n                new LinearSmoothScroller(recyclerView.getContext());\n        smoothScroller.setTargetPosition(position);\n        startSmoothScroll(smoothScroller);\n    }\n\n    /**\n     * @return true if LayoutManager will recycle its children when it is detached from\n     * RecyclerView.\n     */\n    @SuppressWarnings(\"UnusedDeclaration\")\n    public boolean getRecycleChildrenOnDetach() {\n        return mRecycleChildrenOnDetach;\n    }\n\n    /**\n     * Set whether this LayoutManager will recycle its children when it is detached from\n     * RecyclerView.\n     * <p>\n     * If you are using a {@link RecyclerView.RecycledViewPool}, it might be a good idea to set\n     * this flag to <code>true</code> so that views will be available to other RecyclerViews\n     * immediately.\n     * <p>\n     * Note that, setting this flag will result in a performance drop if RecyclerView\n     * is restored.\n     *\n     * @param recycleChildrenOnDetach Whether children should be recycled in detach or not.\n     */\n    @SuppressWarnings(\"UnusedDeclaration\")\n    public void setRecycleChildrenOnDetach(boolean recycleChildrenOnDetach) {\n        mRecycleChildrenOnDetach = recycleChildrenOnDetach;\n    }\n\n    @Override\n    public void onAttachedToWindow(RecyclerView recyclerView) {\n        super.onAttachedToWindow(recyclerView);\n        mParent = (View) recyclerView.getParent();\n    }\n\n    @Override\n    public void onDetachedFromWindow(RecyclerView view, RecyclerView.Recycler recycler) {\n        super.onDetachedFromWindow(view, recycler);\n        if (mRecycleChildrenOnDetach) {\n            if (DEBUG) {\n                Log.d(TAG, \"onDetachedFromWindow. Recycling children in the recycler\");\n            }\n            removeAndRecycleAllViews(recycler);\n            recycler.clear();\n        }\n    }\n\n    @Override\n    public boolean canScrollHorizontally() {\n        if (mFlexWrap == FlexWrap.NOWRAP) {\n            return isMainAxisDirectionHorizontal();\n        } else {\n            return !isMainAxisDirectionHorizontal() || getWidth() > (mParent != null ? mParent.getWidth() : 0);\n        }\n    }\n\n    @Override\n    public boolean canScrollVertically() {\n        if (mFlexWrap == FlexWrap.NOWRAP) {\n            return !isMainAxisDirectionHorizontal();\n        } else {\n            return isMainAxisDirectionHorizontal() || getHeight() > (mParent != null ? mParent.getHeight() : 0);\n        }\n    }\n\n    @Override\n    public int scrollHorizontallyBy(int dx, RecyclerView.Recycler recycler,\n            RecyclerView.State state) {\n        if (!isMainAxisDirectionHorizontal() || (mFlexWrap == FlexWrap.NOWRAP)) {\n            int scrolled = handleScrollingMainOrientation(dx, recycler, state);\n            mViewCache.clear();\n            return scrolled;\n        } else {\n            int scrolled = handleScrollingSubOrientation(dx);\n            mAnchorInfo.mPerpendicularCoordinate += scrolled;\n            mSubOrientationHelper.offsetChildren(-scrolled);\n            return scrolled;\n        }\n    }\n\n    @Override\n    public int scrollVerticallyBy(int dy, RecyclerView.Recycler recycler,\n            RecyclerView.State state) {\n        if (isMainAxisDirectionHorizontal() ||\n                (mFlexWrap == FlexWrap.NOWRAP && !isMainAxisDirectionHorizontal())) {\n            int scrolled = handleScrollingMainOrientation(dy, recycler, state);\n            mViewCache.clear();\n            return scrolled;\n        } else {\n            int scrolled = handleScrollingSubOrientation(dy);\n            mAnchorInfo.mPerpendicularCoordinate += scrolled;\n            mSubOrientationHelper.offsetChildren(-scrolled);\n            return scrolled;\n        }\n    }\n\n    /**\n     * Handle the scrolling along the direction of {@link #mOrientationHelper}.\n     *\n     * @param delta    the delta for the amount that is being scrolled\n     *                 (either horizontally or vertically)\n     * @param recycler the Recycler instance\n     * @param state    the Recycler.State instance\n     * @return the amount actually scrolled\n     */\n    private int handleScrollingMainOrientation(int delta, RecyclerView.Recycler recycler,\n            RecyclerView.State state) {\n        if (getChildCount() == 0 || delta == 0) {\n            return 0;\n        }\n        ensureOrientationHelper();\n        mLayoutState.mShouldRecycle = true;\n        int layoutDirection;\n        boolean columnAndRtl = !isMainAxisDirectionHorizontal() && mIsRtl;\n        if (columnAndRtl) {\n            layoutDirection = delta < 0 ? LayoutState.LAYOUT_END : LayoutState.LAYOUT_START;\n        } else {\n            layoutDirection = delta > 0 ? LayoutState.LAYOUT_END : LayoutState.LAYOUT_START;\n        }\n        int absDelta = Math.abs(delta);\n\n        updateLayoutState(layoutDirection, absDelta);\n\n        int freeScroll = mLayoutState.mScrollingOffset;\n        int consumed = freeScroll + fill(recycler, state, mLayoutState);\n        if (consumed < 0) {\n            return 0;\n        }\n        int scrolled;\n        if (columnAndRtl) {\n            scrolled = absDelta > consumed ? -layoutDirection * consumed : delta;\n        } else {\n            scrolled = absDelta > consumed ? layoutDirection * consumed : delta;\n        }\n        mOrientationHelper.offsetChildren(-scrolled);\n        mLayoutState.mLastScrollDelta = scrolled;\n        return scrolled;\n    }\n\n    /**\n     * Handle the scrolling along the direction of {@link #mSubOrientationHelper}.\n     *\n     * @param delta    the delta for the amount that is being scrolled\n     *                 (either horizontally or vertically)\n     * @return  the amount actually scrolled\n     */\n    private int handleScrollingSubOrientation(int delta) {\n        if (getChildCount() == 0 || delta == 0) {\n            return 0;\n        }\n        ensureOrientationHelper();\n        boolean isMainAxisHorizontal = isMainAxisDirectionHorizontal();\n        int parentLength = isMainAxisHorizontal ? mParent.getWidth() : mParent.getHeight();\n        int mainAxisLength = isMainAxisHorizontal ? getWidth() : getHeight();\n\n        boolean layoutRtl = getLayoutDirection() == ViewCompat.LAYOUT_DIRECTION_RTL;\n        if (layoutRtl) {\n            int absDelta = Math.abs(delta);\n            if (delta < 0) {\n                delta = Math.min(mainAxisLength\n                        + mAnchorInfo.mPerpendicularCoordinate - parentLength, absDelta);\n                delta = -delta;\n            } else {\n                delta = mAnchorInfo.mPerpendicularCoordinate + delta > 0\n                        ? -mAnchorInfo.mPerpendicularCoordinate\n                        : delta;\n            }\n        } else {\n            if (delta > 0) {\n                delta = Math.min(mainAxisLength\n                        - mAnchorInfo.mPerpendicularCoordinate - parentLength, delta);\n            } else {\n                delta = mAnchorInfo.mPerpendicularCoordinate + delta >= 0 ? delta :\n                        -mAnchorInfo.mPerpendicularCoordinate;\n            }\n        }\n        return delta;\n    }\n\n    /**\n     * Update the layout state as part of the scrolling. This method also update the flex lines\n     * enough to display the view port including the delta of the scroll.\n     *\n     * @param layoutDirection the layout direction value. Either of {@link LayoutState#LAYOUT_END}\n     *                        or {@link LayoutState#LAYOUT_START}\n     * @param absDelta        the absolute value of the delta that is about to be scrolled.\n     */\n    private void updateLayoutState(int layoutDirection, int absDelta) {\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        mLayoutState.mLayoutDirection = layoutDirection;\n        boolean mainAxisHorizontal = isMainAxisDirectionHorizontal();\n\n        //noinspection ResourceType\n        int widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(getWidth(), getWidthMode());\n        //noinspection ResourceType\n        int heightMeasureSpec = View.MeasureSpec.makeMeasureSpec(getHeight(), getHeightMode());\n        boolean columnAndRtl = !mainAxisHorizontal && mIsRtl;\n        if (layoutDirection == LayoutState.LAYOUT_END) {\n            View lastVisible = getChildAt(getChildCount() - 1);\n            if (lastVisible == null) {\n                return;\n            }\n            mLayoutState.mOffset = mOrientationHelper.getDecoratedEnd(lastVisible);\n            int lastVisiblePosition = getPosition(lastVisible);\n            int lastVisibleLinePosition = mFlexboxHelper.mIndexToFlexLine[lastVisiblePosition];\n            FlexLine lastVisibleLine = mFlexLines.get(lastVisibleLinePosition);\n\n            // The reference view which has the maximum end (or minimum if the layout is RTL and\n            // the main axis direction is horizontal) coordinate in  the last visible flex line.\n            View referenceView = findLastReferenceViewInLine(lastVisible, lastVisibleLine);\n            mLayoutState.mItemDirection = LayoutState.ITEM_DIRECTION_TAIL;\n            mLayoutState.mPosition = lastVisiblePosition + mLayoutState.mItemDirection;\n            if (mFlexboxHelper.mIndexToFlexLine.length <= mLayoutState.mPosition) {\n                mLayoutState.mFlexLinePosition = NO_POSITION;\n            } else {\n                mLayoutState.mFlexLinePosition\n                        = mFlexboxHelper.mIndexToFlexLine[mLayoutState.mPosition];\n            }\n\n            if (columnAndRtl) {\n                mLayoutState.mOffset = mOrientationHelper.getDecoratedStart(referenceView);\n                mLayoutState.mScrollingOffset = -mOrientationHelper.getDecoratedStart(referenceView)\n                        + mOrientationHelper.getStartAfterPadding();\n                mLayoutState.mScrollingOffset = Math.max(mLayoutState.mScrollingOffset, 0);\n            } else {\n                mLayoutState.mOffset = mOrientationHelper.getDecoratedEnd(referenceView);\n                mLayoutState.mScrollingOffset = mOrientationHelper.getDecoratedEnd(referenceView)\n                        - mOrientationHelper.getEndAfterPadding();\n            }\n\n            if ((mLayoutState.mFlexLinePosition == NO_POSITION\n                    || mLayoutState.mFlexLinePosition > mFlexLines.size() - 1) &&\n                    mLayoutState.mPosition <= getFlexItemCount()) {\n                // If the RecyclerView tries to scroll beyond the already calculated\n                // flex container, need to calculate beyond the amount that needs to be filled\n\n                int needsToFill = absDelta - mLayoutState.mScrollingOffset;\n                mFlexLinesResult.reset();\n                if (needsToFill > 0) {\n                    if (mainAxisHorizontal) {\n                        mFlexboxHelper.calculateHorizontalFlexLines(mFlexLinesResult,\n                                widthMeasureSpec, heightMeasureSpec, needsToFill,\n                                mLayoutState.mPosition, mFlexLines);\n                    } else {\n                        mFlexboxHelper.calculateVerticalFlexLines(mFlexLinesResult,\n                                widthMeasureSpec, heightMeasureSpec, needsToFill,\n                                mLayoutState.mPosition, mFlexLines);\n                    }\n                    mFlexboxHelper.determineMainSize(widthMeasureSpec, heightMeasureSpec,\n                            mLayoutState.mPosition);\n                    mFlexboxHelper.stretchViews(mLayoutState.mPosition);\n                }\n            }\n        } else {\n            View firstVisible = getChildAt(0);\n            if (firstVisible == null) {\n                return;\n            }\n            mLayoutState.mOffset = mOrientationHelper.getDecoratedStart(firstVisible);\n            int firstVisiblePosition = getPosition(firstVisible);\n            int firstVisibleLinePosition = mFlexboxHelper.mIndexToFlexLine[firstVisiblePosition];\n            FlexLine firstVisibleLine = mFlexLines.get(firstVisibleLinePosition);\n\n            // The reference view which has the minimum start (or maximum if the layout is RTL and\n            // the main axis direction is horizontal) coordinate in the first visible flex line\n            View referenceView = findFirstReferenceViewInLine(firstVisible, firstVisibleLine);\n\n            mLayoutState.mItemDirection = LayoutState.ITEM_DIRECTION_TAIL;\n            int flexLinePosition = mFlexboxHelper.mIndexToFlexLine[firstVisiblePosition];\n            if (flexLinePosition == NO_POSITION) {\n                flexLinePosition = 0;\n            }\n            if (flexLinePosition > 0) {\n                FlexLine previousLine = mFlexLines.get(flexLinePosition - 1);\n                // The position of the next item toward start should be on the next flex line,\n                // shifting the position by the number of the items in the previous line.\n                mLayoutState.mPosition = firstVisiblePosition - previousLine.getItemCount();\n            } else {\n                mLayoutState.mPosition = NO_POSITION;\n            }\n            mLayoutState.mFlexLinePosition = flexLinePosition > 0 ? flexLinePosition - 1 : 0;\n\n            if (columnAndRtl) {\n                mLayoutState.mOffset = mOrientationHelper.getDecoratedEnd(referenceView);\n                mLayoutState.mScrollingOffset = mOrientationHelper.getDecoratedEnd(referenceView)\n                        - mOrientationHelper.getEndAfterPadding();\n                mLayoutState.mScrollingOffset = Math.max(mLayoutState.mScrollingOffset, 0);\n            } else {\n                mLayoutState.mOffset = mOrientationHelper.getDecoratedStart(referenceView);\n                mLayoutState.mScrollingOffset = -mOrientationHelper.getDecoratedStart(referenceView)\n                        + mOrientationHelper.getStartAfterPadding();\n            }\n        }\n        mLayoutState.mAvailable = absDelta - mLayoutState.mScrollingOffset;\n    }\n\n    /**\n     * Loop through the first visible flex line to find the reference view, which has the minimum\n     * start (or maximum if the layout is RTL and main axis direction is horizontal) coordinate.\n     *\n     * @param firstView        the first visible view\n     * @param firstVisibleLine the first visible flex line\n     * @return the reference view\n     */\n    private View findFirstReferenceViewInLine(View firstView, FlexLine firstVisibleLine) {\n        boolean mainAxisHorizontal = isMainAxisDirectionHorizontal();\n        View referenceView = firstView;\n        for (int i = 1, to = firstVisibleLine.mItemCount;\n                i < to; i++) {\n            View viewInSameLine = getChildAt(i);\n            if (viewInSameLine == null || viewInSameLine.getVisibility() == View.GONE) {\n                continue;\n            }\n            if (mIsRtl && !mainAxisHorizontal) {\n                if (mOrientationHelper.getDecoratedEnd(referenceView)\n                        < mOrientationHelper.getDecoratedEnd(viewInSameLine)) {\n                    referenceView = viewInSameLine;\n                }\n            } else {\n                if (mOrientationHelper.getDecoratedStart(referenceView)\n                        > mOrientationHelper.getDecoratedStart(viewInSameLine)) {\n                    referenceView = viewInSameLine;\n                }\n            }\n        }\n        return referenceView;\n    }\n\n    /**\n     * Loop through the last visible flex line to find the reference view, which has the maximum\n     * end (or minimum if the layout is RTL and main axis direction is horizontal) coordinate.\n     *\n     * @param lastView        the last visible view\n     * @param lastVisibleLine the last visible flex line\n     * @return the reference view\n     */\n    private View findLastReferenceViewInLine(View lastView, FlexLine lastVisibleLine) {\n        boolean mainAxisHorizontal = isMainAxisDirectionHorizontal();\n        View referenceView = lastView;\n        for (int i = getChildCount() - 2, to = getChildCount() - lastVisibleLine.mItemCount - 1;\n                i > to; i--) {\n            View viewInSameLine = getChildAt(i);\n            if (viewInSameLine == null || viewInSameLine.getVisibility() == View.GONE) {\n                continue;\n            }\n            if (mIsRtl && !mainAxisHorizontal) {\n                // The end edge of the view is left, should be the minimum left edge\n                // where the next view should be placed\n                if (mOrientationHelper.getDecoratedStart(referenceView) >\n                        mOrientationHelper.getDecoratedStart(viewInSameLine)) {\n                    referenceView = viewInSameLine;\n                }\n            } else {\n                if (mOrientationHelper.getDecoratedEnd(referenceView) <\n                        mOrientationHelper.getDecoratedEnd(viewInSameLine)) {\n                    referenceView = viewInSameLine;\n                }\n            }\n        }\n        return referenceView;\n    }\n\n    @Override\n    public int computeHorizontalScrollExtent(@NonNull RecyclerView.State state) {\n        int scrollExtent = computeScrollExtent(state);\n        if (DEBUG) {\n            Log.d(TAG, \"computeHorizontalScrollExtent: \" + scrollExtent);\n        }\n        return scrollExtent;\n    }\n\n    @Override\n    public int computeVerticalScrollExtent(@NonNull RecyclerView.State state) {\n        int scrollExtent = computeScrollExtent(state);\n        if (DEBUG) {\n            Log.d(TAG, \"computeVerticalScrollExtent: \" + scrollExtent);\n        }\n        return scrollExtent;\n    }\n\n    private int computeScrollExtent(RecyclerView.State state) {\n        if (getChildCount() == 0) {\n            return 0;\n        }\n        int allChildrenCount = state.getItemCount();\n        ensureOrientationHelper();\n        View firstReferenceView = findFirstReferenceChild(allChildrenCount);\n        View lastReferenceView = findLastReferenceChild(allChildrenCount);\n        if (state.getItemCount() == 0 || firstReferenceView == null || lastReferenceView == null) {\n            return 0;\n        }\n        // TODO: Need to consider the reverse pattern when flexWrap == wrap_reverse is implemented\n        int extend = mOrientationHelper.getDecoratedEnd(lastReferenceView) -\n                mOrientationHelper.getDecoratedStart(firstReferenceView);\n        return Math.min(mOrientationHelper.getTotalSpace(), extend);\n    }\n\n    @Override\n    public int computeHorizontalScrollOffset(@NonNull RecyclerView.State state) {\n        int scrollOffset = computeScrollOffset(state);\n        if (DEBUG) {\n            Log.d(TAG, \"computeHorizontalScrollOffset: \" + scrollOffset);\n        }\n        return scrollOffset;\n    }\n\n    @Override\n    public int computeVerticalScrollOffset(@NonNull RecyclerView.State state) {\n        int scrollOffset = computeScrollOffset(state);\n        if (DEBUG) {\n            Log.d(TAG, \"computeVerticalScrollOffset: \" + scrollOffset);\n        }\n        return scrollOffset;\n    }\n\n    private int computeScrollOffset(RecyclerView.State state) {\n        if (getChildCount() == 0) {\n            return 0;\n        }\n        int allChildrenCount = state.getItemCount();\n        View firstReferenceView = findFirstReferenceChild(allChildrenCount);\n        View lastReferenceView = findLastReferenceChild(allChildrenCount);\n        if (state.getItemCount() == 0 || firstReferenceView == null || lastReferenceView == null) {\n            return 0;\n        }\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        int minPosition = getPosition(firstReferenceView);\n        int maxPosition = getPosition(lastReferenceView);\n        int laidOutArea = Math.abs(mOrientationHelper.getDecoratedEnd(lastReferenceView) -\n                mOrientationHelper.getDecoratedStart(firstReferenceView));\n        int firstLinePosition = mFlexboxHelper.mIndexToFlexLine[minPosition];\n        if (firstLinePosition == 0 || firstLinePosition == NO_POSITION) {\n            return 0;\n        }\n        int lastLinePosition = mFlexboxHelper.mIndexToFlexLine[maxPosition];\n        int lineRange = lastLinePosition - firstLinePosition + 1;\n        float averageSizePerLine = (float) laidOutArea / lineRange;\n        // The number of lines before the first line is equal to the value of firstLinePosition\n        return Math.round(\n                firstLinePosition * averageSizePerLine + (mOrientationHelper.getStartAfterPadding()\n                        - mOrientationHelper.getDecoratedStart(firstReferenceView)));\n    }\n\n    @Override\n    public int computeHorizontalScrollRange(@NonNull RecyclerView.State state) {\n        int scrollRange = computeScrollRange(state);\n        if (DEBUG) {\n            Log.d(TAG, \"computeHorizontalScrollRange: \" + scrollRange);\n        }\n        return scrollRange;\n    }\n\n    @Override\n    public int computeVerticalScrollRange(@NonNull RecyclerView.State state) {\n        int scrollRange = computeScrollRange(state);\n        if (DEBUG) {\n            Log.d(TAG, \"computeVerticalScrollRange: \" + scrollRange);\n        }\n        return scrollRange;\n    }\n\n    /**\n     * @return the estimate total length of the flex container.\n     * Note that this method estimates the length by using the number of the visible items and the\n     * rest of the non-visible items. So the value returned by this method isn't the exact length\n     * of the container. So the scroll bar position may be slightly different from the actual\n     * expected position\n     */\n    private int computeScrollRange(RecyclerView.State state) {\n        if (getChildCount() == 0) {\n            return 0;\n        }\n        int allItemCount = state.getItemCount();\n        View firstReferenceView = findFirstReferenceChild(allItemCount);\n        View lastReferenceView = findLastReferenceChild(allItemCount);\n        if (state.getItemCount() == 0 || firstReferenceView == null || lastReferenceView == null) {\n            return 0;\n        }\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        int firstVisiblePosition = findFirstVisibleItemPosition();\n        int lastVisiblePosition = findLastVisibleItemPosition();\n        int laidOutArea = Math.abs(mOrientationHelper.getDecoratedEnd(lastReferenceView) -\n                mOrientationHelper.getDecoratedStart(firstReferenceView));\n        int laidOutRange = lastVisiblePosition - firstVisiblePosition + 1;\n        return (int) ((float) laidOutArea / laidOutRange * state.getItemCount());\n    }\n\n    /**\n     * Copied from {@link RecyclerView.LayoutManager#shouldMeasureChild\n     * (View,\n     * int, int, RecyclerView.LayoutParams)}}\n     */\n    private boolean shouldMeasureChild(View child, int widthSpec, int heightSpec,\n            RecyclerView.LayoutParams lp) {\n        return child.isLayoutRequested()\n                || !isMeasurementCacheEnabled()\n                || !isMeasurementUpToDate(child.getWidth(), widthSpec, lp.width)\n                || !isMeasurementUpToDate(child.getHeight(), heightSpec, lp.height);\n    }\n\n    /**\n     * Copied from\n     * {@link RecyclerView.LayoutManager#isMeasurementUpToDate(int, int,\n     * int)}\n     */\n    private static boolean isMeasurementUpToDate(int childSize, int spec, int dimension) {\n        final int specMode = View.MeasureSpec.getMode(spec);\n        final int specSize = View.MeasureSpec.getSize(spec);\n        if (dimension > 0 && childSize != dimension) {\n            return false;\n        }\n        switch (specMode) {\n            case View.MeasureSpec.UNSPECIFIED:\n                return true;\n            case View.MeasureSpec.AT_MOST:\n                return specSize >= childSize;\n            case View.MeasureSpec.EXACTLY:\n                return specSize == childSize;\n        }\n        return false;\n    }\n\n    private void clearFlexLines() {\n        mFlexLines.clear();\n        mAnchorInfo.reset();\n        mAnchorInfo.mPerpendicularCoordinate = 0;\n    }\n\n    private int getChildLeft(View view) {\n        RecyclerView.LayoutParams params = (RecyclerView.LayoutParams)\n                view.getLayoutParams();\n        return getDecoratedLeft(view) - params.leftMargin;\n    }\n\n    private int getChildRight(View view) {\n        RecyclerView.LayoutParams params = (RecyclerView.LayoutParams)\n                view.getLayoutParams();\n        return getDecoratedRight(view) + params.rightMargin;\n    }\n\n    private int getChildTop(View view) {\n        RecyclerView.LayoutParams params = (RecyclerView.LayoutParams)\n                view.getLayoutParams();\n        return getDecoratedTop(view) - params.topMargin;\n    }\n\n    private int getChildBottom(View view) {\n        RecyclerView.LayoutParams params = (RecyclerView.LayoutParams)\n                view.getLayoutParams();\n        return getDecoratedBottom(view) + params.bottomMargin;\n    }\n\n    /**\n     * @param view              the view to be examined if it's visible\n     * @param completelyVisible when passed as {@code true}, this method checks if the view bounds\n     *                          don't overlap the bounds of the RecyclerView. When passed as\n     *                          {@code false}, this method checks if the view bounds are partially\n     *                          visible within the RecyclerView.\n     * @return if the view passed as an argument is visible (view bounds are within the parent\n     * RecyclerView)\n     */\n    private boolean isViewVisible(View view, boolean completelyVisible) {\n        int left = getPaddingLeft();\n        int top = getPaddingTop();\n        int right = getWidth() - getPaddingRight();\n        int bottom = getHeight() - getPaddingBottom();\n        int childLeft = getChildLeft(view);\n        int childTop = getChildTop(view);\n        int childRight = getChildRight(view);\n        int childBottom = getChildBottom(view);\n\n        boolean horizontalCompletelyVisible = false;\n        boolean horizontalPartiallyVisible = false;\n        boolean verticalCompletelyVisible = false;\n        boolean verticalPartiallyVisible = false;\n        if (left <= childLeft && right >= childRight) {\n            horizontalCompletelyVisible = true;\n        }\n        if (childLeft >= right || childRight >= left) {\n            horizontalPartiallyVisible = true;\n        }\n\n        if (top <= childTop && bottom >= childBottom) {\n            verticalCompletelyVisible = true;\n        }\n        if (childTop >= bottom || childBottom >= top) {\n            verticalPartiallyVisible = true;\n        }\n        if (completelyVisible) {\n            return horizontalCompletelyVisible && verticalCompletelyVisible;\n        } else {\n            return horizontalPartiallyVisible && verticalPartiallyVisible;\n        }\n    }\n\n    /**\n     * Returns the adapter position of the first visible view. This position does not include\n     * adapter changes that were dispatched after the last layout pass.\n     *\n     * If RecyclerView has item decorators, they will be considered in calculations as well.\n     * LayoutManager may pre-cache some views that are not necessarily visible. Those views\n     * are ignored in this method.\n     *\n     * @return The adapter position of the first visible item or {@link RecyclerView#NO_POSITION} if\n     * there aren't any visible items.\n     * @see #findFirstCompletelyVisibleItemPosition()\n     * @see #findLastVisibleItemPosition()\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public int findFirstVisibleItemPosition() {\n        final View child = findOneVisibleChild(0, getChildCount(), false);\n        return child == null ? NO_POSITION : getPosition(child);\n    }\n\n    /**\n     * Returns the adapter position of the first fully visible view. This position does not include\n     * adapter changes that were dispatched after the last layout pass.\n     *\n     * @return The adapter position of the first fully visible item or\n     * {@link RecyclerView#NO_POSITION} if there aren't any visible items.\n     * @see #findFirstVisibleItemPosition()\n     * @see #findLastCompletelyVisibleItemPosition()\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public int findFirstCompletelyVisibleItemPosition() {\n        final View child = findOneVisibleChild(0, getChildCount(), true);\n        return child == null ? NO_POSITION : getPosition(child);\n    }\n\n    /**\n     * Returns the adapter position of the last visible view. This position does not include\n     * adapter changes that were dispatched after the last layout pass.\n     *\n     * If RecyclerView has item decorators, they will be considered in calculations as well.\n     * LayoutManager may pre-cache some views that are not necessarily visible. Those views\n     * are ignored in this method.\n     *\n     * @return The adapter position of the last visible view or {@link RecyclerView#NO_POSITION} if\n     * there aren't any visible items.\n     * @see #findLastCompletelyVisibleItemPosition()\n     * @see #findFirstVisibleItemPosition()\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public int findLastVisibleItemPosition() {\n        final View child = findOneVisibleChild(getChildCount() - 1, -1, false);\n        return child == null ? NO_POSITION : getPosition(child);\n    }\n\n    /**\n     * Returns the adapter position of the last fully visible view. This position does not include\n     * adapter changes that were dispatched after the last layout pass.\n     *\n     * @return The adapter position of the last fully visible view or\n     * {@link RecyclerView#NO_POSITION} if there aren't any visible items.\n     * @see #findLastVisibleItemPosition()\n     * @see #findFirstCompletelyVisibleItemPosition()\n     */\n    @SuppressWarnings(\"WeakerAccess\")\n    public int findLastCompletelyVisibleItemPosition() {\n        final View child = findOneVisibleChild(getChildCount() - 1, -1, true);\n        return child == null ? NO_POSITION : getPosition(child);\n    }\n\n    /**\n     * Returns the first child that is visible in the provided index range, i.e. either partially or\n     * fully visible depending on the arguments provided.\n     *\n     * @param fromIndex         the start index for searching the visible child\n     * @param toIndex           the last index for searching the visible child\n     * @param completelyVisible when passed as {@code true}, this method checks if the view bounds\n     *                          don't overlap the bounds of the RecyclerView. When passed as\n     *                          {@code false}, this method checks if the view bounds are partially\n     *                          visible within the RecyclerView.\n     * @return the first child that is visible.\n     */\n    private View findOneVisibleChild(int fromIndex, int toIndex, boolean completelyVisible) {\n        int next = toIndex > fromIndex ? 1 : -1;\n        for (int i = fromIndex; i != toIndex; i += next) {\n            View view = getChildAt(i);\n            if (isViewVisible(view, completelyVisible)) {\n                return view;\n            }\n        }\n        return null;\n    }\n\n    /**\n     * @param position the index of the view\n     * @return the index of the {@link FlexLine}, which includes the view whose index is passed as\n     * the position argument.\n     */\n    int getPositionToFlexLineIndex(int position) {\n        assert mFlexboxHelper.mIndexToFlexLine != null;\n        return mFlexboxHelper.mIndexToFlexLine[position];\n    }\n\n    /**\n     * LayoutParams used by the {@link FlexboxLayoutManager}, which stores per-child information\n     * required for the Flexbox.\n     *\n     * Note that some parent fields (which are not primitive nor a class implements\n     * {@link Parcelable}) are not included as the stored/restored fields after this class\n     * is serialized/de-serialized as an {@link Parcelable}.\n     */\n    public static class LayoutParams extends RecyclerView.LayoutParams implements FlexItem {\n\n        /**\n         * @see FlexItem#getFlexGrow()\n         */\n        private float mFlexGrow = FlexItem.FLEX_GROW_DEFAULT;\n\n        /**\n         * @see FlexItem#getFlexShrink()\n         */\n        private float mFlexShrink = FlexItem.FLEX_SHRINK_DEFAULT;\n\n        /**\n         * @see FlexItem#getAlignSelf()\n         */\n        private int mAlignSelf = AlignSelf.AUTO;\n\n        /**\n         * @see FlexItem#getFlexBasisPercent()\n         */\n        private float mFlexBasisPercent = FlexItem.FLEX_BASIS_PERCENT_DEFAULT;\n\n        /**\n         * @see FlexItem#getMinWidth()\n         */\n        private int mMinWidth;\n\n        /**\n         * @see FlexItem#getMinHeight()\n         */\n        private int mMinHeight;\n\n        /**\n         * @see FlexItem#getMaxWidth()\n         */\n        private int mMaxWidth = MAX_SIZE;\n\n        /**\n         * @see FlexItem#getMaxHeight()\n         */\n        private int mMaxHeight = MAX_SIZE;\n\n        /**\n         * @see FlexItem#isWrapBefore()\n         */\n        private boolean mWrapBefore;\n\n        @Override\n        public int getWidth() {\n            return width;\n        }\n\n        @Override\n        public void setWidth(int width) {\n            this.width = width;\n        }\n\n        @Override\n        public int getHeight() {\n            return height;\n        }\n\n        @Override\n        public void setHeight(int height) {\n            this.height = height;\n        }\n\n        @Override\n        public float getFlexGrow() {\n            return mFlexGrow;\n        }\n\n        @Override\n        public void setFlexGrow(float flexGrow) {\n            this.mFlexGrow = flexGrow;\n        }\n\n        @Override\n        public float getFlexShrink() {\n            return mFlexShrink;\n        }\n\n        @Override\n        public void setFlexShrink(float flexShrink) {\n            this.mFlexShrink = flexShrink;\n        }\n\n        @AlignSelf\n        @Override\n        public int getAlignSelf() {\n            return mAlignSelf;\n        }\n\n        @Override\n        public void setAlignSelf(@AlignSelf int alignSelf) {\n            this.mAlignSelf = alignSelf;\n        }\n\n        @Override\n        public int getMinWidth() {\n            return mMinWidth;\n        }\n\n        @Override\n        public void setMinWidth(int minWidth) {\n            this.mMinWidth = minWidth;\n        }\n\n        @Override\n        public int getMinHeight() {\n            return mMinHeight;\n        }\n\n        @Override\n        public void setMinHeight(int minHeight) {\n            this.mMinHeight = minHeight;\n        }\n\n        @Override\n        public int getMaxWidth() {\n            return mMaxWidth;\n        }\n\n        @Override\n        public void setMaxWidth(int maxWidth) {\n            this.mMaxWidth = maxWidth;\n        }\n\n        @Override\n        public int getMaxHeight() {\n            return mMaxHeight;\n        }\n\n        @Override\n        public void setMaxHeight(int maxHeight) {\n            this.mMaxHeight = maxHeight;\n        }\n\n        @Override\n        public boolean isWrapBefore() {\n            return mWrapBefore;\n        }\n\n        @Override\n        public void setWrapBefore(boolean wrapBefore) {\n            this.mWrapBefore = wrapBefore;\n        }\n\n        @Override\n        public float getFlexBasisPercent() {\n            return mFlexBasisPercent;\n        }\n\n        @Override\n        public void setFlexBasisPercent(float flexBasisPercent) {\n            this.mFlexBasisPercent = flexBasisPercent;\n        }\n\n        @Override\n        public int getMarginLeft() {\n            return leftMargin;\n        }\n\n        @Override\n        public int getMarginTop() {\n            return topMargin;\n        }\n\n        @Override\n        public int getMarginRight() {\n            return rightMargin;\n        }\n\n        @Override\n        public int getMarginBottom() {\n            return bottomMargin;\n        }\n\n        public LayoutParams(Context c, AttributeSet attrs) {\n            super(c, attrs);\n        }\n\n        public LayoutParams(int width, int height) {\n            super(width, height);\n        }\n\n        public LayoutParams(ViewGroup.MarginLayoutParams source) {\n            super(source);\n        }\n\n        public LayoutParams(ViewGroup.LayoutParams source) {\n            super(source);\n        }\n\n        public LayoutParams(RecyclerView.LayoutParams source) {\n            super(source);\n        }\n\n        public LayoutParams(LayoutParams source) {\n            super(source);\n\n            mFlexGrow = source.mFlexGrow;\n            mFlexShrink = source.mFlexShrink;\n            mAlignSelf = source.mAlignSelf;\n            mFlexBasisPercent = source.mFlexBasisPercent;\n            mMinWidth = source.mMinWidth;\n            mMinHeight = source.mMinHeight;\n            mMaxWidth = source.mMaxWidth;\n            mMaxHeight = source.mMaxHeight;\n            mWrapBefore = source.mWrapBefore;\n        }\n\n        @Override\n        public int getOrder() {\n            return FlexItem.ORDER_DEFAULT;\n        }\n\n        @Override\n        public void setOrder(int order) {\n            // Unlike the FlexboxLayout, the order attribute is not supported, we don't calculate\n            // the order attribute because preparing the order attribute requires all\n            // view holders to be inflated at least once, which is inefficient if the number of\n            // items in the adapter is large\n            throw new UnsupportedOperationException(\"Setting the order in the \"\n                    + \"FlexboxLayoutManager is not supported. Use FlexboxLayout \"\n                    + \"if you need to reorder using the attribute.\");\n        }\n\n        @Override\n        public int describeContents() {\n            return 0;\n        }\n\n        @Override\n        public void writeToParcel(Parcel dest, int flags) {\n            dest.writeFloat(this.mFlexGrow);\n            dest.writeFloat(this.mFlexShrink);\n            dest.writeInt(this.mAlignSelf);\n            dest.writeFloat(this.mFlexBasisPercent);\n            dest.writeInt(this.mMinWidth);\n            dest.writeInt(this.mMinHeight);\n            dest.writeInt(this.mMaxWidth);\n            dest.writeInt(this.mMaxHeight);\n            dest.writeByte(this.mWrapBefore ? (byte) 1 : (byte) 0);\n            dest.writeInt(this.bottomMargin);\n            dest.writeInt(this.leftMargin);\n            dest.writeInt(this.rightMargin);\n            dest.writeInt(this.topMargin);\n            dest.writeInt(this.height);\n            dest.writeInt(this.width);\n        }\n\n        protected LayoutParams(Parcel in) {\n            super(WRAP_CONTENT, WRAP_CONTENT);\n            this.mFlexGrow = in.readFloat();\n            this.mFlexShrink = in.readFloat();\n            this.mAlignSelf = in.readInt();\n            this.mFlexBasisPercent = in.readFloat();\n            this.mMinWidth = in.readInt();\n            this.mMinHeight = in.readInt();\n            this.mMaxWidth = in.readInt();\n            this.mMaxHeight = in.readInt();\n            this.mWrapBefore = in.readByte() != 0;\n            this.bottomMargin = in.readInt();\n            this.leftMargin = in.readInt();\n            this.rightMargin = in.readInt();\n            this.topMargin = in.readInt();\n            this.height = in.readInt();\n            this.width = in.readInt();\n        }\n\n        public static final Parcelable.Creator<LayoutParams> CREATOR\n                = new Parcelable.Creator<LayoutParams>() {\n            @Override\n            public LayoutParams createFromParcel(Parcel source) {\n                return new LayoutParams(source);\n            }\n\n            @Override\n            public LayoutParams[] newArray(int size) {\n                return new LayoutParams[size];\n            }\n        };\n    }\n\n    /**\n     * A class that holds the information about an anchor position like from what pixels layout\n     * should start.\n     */\n    private class AnchorInfo {\n\n        private int mPosition;\n\n        private int mFlexLinePosition;\n\n        private int mCoordinate;\n\n        /**\n         * The anchor position of the main axis, which is the secondary scrolling direction.\n         */\n        private int mPerpendicularCoordinate = 0;\n\n        private boolean mLayoutFromEnd;\n\n        private boolean mValid;\n\n        private boolean mAssignedFromSavedState;\n\n        private void reset() {\n            mPosition = NO_POSITION;\n            mFlexLinePosition = NO_POSITION;\n            mCoordinate = INVALID_OFFSET;\n            mValid = false;\n            mAssignedFromSavedState = false;\n            if (isMainAxisDirectionHorizontal()) {\n                if (mFlexWrap == FlexWrap.NOWRAP) {\n                    mLayoutFromEnd = mFlexDirection == FlexDirection.ROW_REVERSE;\n                } else {\n                    mLayoutFromEnd = mFlexWrap == FlexWrap.WRAP_REVERSE;\n                }\n            } else {\n                if (mFlexWrap == FlexWrap.NOWRAP) {\n                    mLayoutFromEnd = mFlexDirection == FlexDirection.COLUMN_REVERSE;\n                } else {\n                    mLayoutFromEnd = mFlexWrap == FlexWrap.WRAP_REVERSE;\n                }\n            }\n        }\n\n        private void assignCoordinateFromPadding() {\n            if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n                mCoordinate = mLayoutFromEnd ? mOrientationHelper.getEndAfterPadding()\n                        : getWidth() - mOrientationHelper.getStartAfterPadding();\n            } else {\n                mCoordinate = mLayoutFromEnd ? mOrientationHelper.getEndAfterPadding()\n                        : mOrientationHelper.getStartAfterPadding();\n            }\n        }\n\n        private void assignFromView(View anchor) {\n            OrientationHelper orientationHelper;\n            // When the flex wrap is nowrap, the orientation helper is changed to\n            // perpendicular. Need to use the mSubOrientationHelper to be consistent with\n            // when flex wrap is not nowrap.\n            if (mFlexWrap == FlexWrap.NOWRAP) {\n                orientationHelper = mSubOrientationHelper;\n            } else {\n                orientationHelper = mOrientationHelper;\n            }\n            if (!isMainAxisDirectionHorizontal() && mIsRtl) {\n                // We need to use the anchor view as starting from right if the flex direction is\n                // (column or column_reverse) and layout direction is RTL.\n                if (mLayoutFromEnd) {\n                    mCoordinate = orientationHelper.getDecoratedStart(anchor) +\n                        orientationHelper.getTotalSpaceChange();\n                } else {\n                    mCoordinate = orientationHelper.getDecoratedEnd(anchor);\n                }\n            } else {\n                if (mLayoutFromEnd) {\n                    mCoordinate = orientationHelper.getDecoratedEnd(anchor) +\n                        orientationHelper.getTotalSpaceChange();\n                } else {\n                    mCoordinate = orientationHelper.getDecoratedStart(anchor);\n                }\n            }\n            mPosition = getPosition(anchor);\n            mAssignedFromSavedState = false;\n            assert mFlexboxHelper.mIndexToFlexLine != null;\n            int flexLinePosition =\n                    mFlexboxHelper.mIndexToFlexLine[mPosition != NO_POSITION ? mPosition : 0];\n            mFlexLinePosition = flexLinePosition != NO_POSITION ? flexLinePosition : 0;\n            // It's likely that the view is the first item in a flex line, but if not get the\n            // index of the first item in the same line because the calculation of the flex lines\n            // expects that it starts from the first item in a flex line\n            if (mFlexLines.size() > mFlexLinePosition) {\n                mPosition = mFlexLines.get(mFlexLinePosition).mFirstIndex;\n            }\n        }\n\n        @Override\n        @NonNull\n        public String toString() {\n            return \"AnchorInfo{\" +\n                    \"mPosition=\" + mPosition +\n                    \", mFlexLinePosition=\" + mFlexLinePosition +\n                    \", mCoordinate=\" + mCoordinate +\n                    \", mPerpendicularCoordinate=\" + mPerpendicularCoordinate +\n                    \", mLayoutFromEnd=\" + mLayoutFromEnd +\n                    \", mValid=\" + mValid +\n                    \", mAssignedFromSavedState=\" + mAssignedFromSavedState +\n                    '}';\n        }\n    }\n\n    /**\n     * Helper class that keeps temporary state while the FlexboxLayoutManager is filling out the\n     * empty space.\n     */\n    private static class LayoutState {\n\n        private final static int SCROLLING_OFFSET_NaN = Integer.MIN_VALUE;\n\n        private static final int LAYOUT_START = -1;\n        private static final int LAYOUT_END = 1;\n\n        private static final int ITEM_DIRECTION_TAIL = 1;\n\n        /** Number of pixels that we should fill, in the layout direction. */\n        private int mAvailable;\n\n        /** If set to true, the value of {@link #mAvailable} is considered as infinite. */\n        private boolean mInfinite;\n\n        // TODO: Add mExtra to support better smooth scrolling\n\n        /** Current position on the flex lines being laid out in the layout call */\n        private int mFlexLinePosition;\n\n        /** Current position on the adapter to get the next item. */\n        private int mPosition;\n\n        /** Pixel offset where layout should start */\n        private int mOffset;\n\n        /**\n         * Used when LayoutState is constructed in a scrolling state.\n         * It should be set the amount of scrolling we can make without creating a new view.\n         * Settings this is required for efficient view recycling.\n         */\n        private int mScrollingOffset;\n\n        /**\n         * The most recent\n         * {@link #scrollVerticallyBy(int, RecyclerView.Recycler, RecyclerView.State)} or\n         * {@link #scrollHorizontallyBy(int, RecyclerView.Recycler, RecyclerView.State)} amount.\n         */\n        private int mLastScrollDelta;\n\n        private int mItemDirection = LayoutState.ITEM_DIRECTION_TAIL;\n\n        private int mLayoutDirection = LayoutState.LAYOUT_END;\n\n        private boolean mShouldRecycle;\n\n        /**\n         * @return {@code true} if there are more items to layout\n         */\n        private boolean hasMore(RecyclerView.State state, List<FlexLine> flexLines) {\n            return mPosition >= 0 && mPosition < state.getItemCount() &&\n                    mFlexLinePosition >= 0 && mFlexLinePosition < flexLines.size();\n        }\n\n        @Override\n        @NonNull\n        public String toString() {\n            return \"LayoutState{\" +\n                    \"mAvailable=\" + mAvailable +\n                    \", mFlexLinePosition=\" + mFlexLinePosition +\n                    \", mPosition=\" + mPosition +\n                    \", mOffset=\" + mOffset +\n                    \", mScrollingOffset=\" + mScrollingOffset +\n                    \", mLastScrollDelta=\" + mLastScrollDelta +\n                    \", mItemDirection=\" + mItemDirection +\n                    \", mLayoutDirection=\" + mLayoutDirection +\n                    '}';\n        }\n    }\n\n    /**\n     * The saved state that needs to be restored after the RecyclerView is recreated.\n     */\n    private static class SavedState implements Parcelable {\n\n        /** The adapter position of the first visible view */\n        private int mAnchorPosition;\n\n        /**\n         * The offset of the first visible view.\n         * E.g. if this value is set as -30, the fist visible view's top is off screen by 30 pixels\n         */\n        private int mAnchorOffset;\n\n        @Override\n        public int describeContents() {\n            return 0;\n        }\n\n        @Override\n        public void writeToParcel(Parcel dest, int flags) {\n            dest.writeInt(this.mAnchorPosition);\n            dest.writeInt(this.mAnchorOffset);\n        }\n\n        SavedState() {\n        }\n\n        private SavedState(Parcel in) {\n            this.mAnchorPosition = in.readInt();\n            this.mAnchorOffset = in.readInt();\n        }\n\n        private SavedState(SavedState savedState) {\n            mAnchorPosition = savedState.mAnchorPosition;\n            mAnchorOffset = savedState.mAnchorOffset;\n        }\n\n        private void invalidateAnchor() {\n            mAnchorPosition = NO_POSITION;\n        }\n\n        private boolean hasValidAnchor(int itemCount) {\n            return mAnchorPosition >= 0 && mAnchorPosition < itemCount;\n        }\n\n        public static final Creator<SavedState> CREATOR = new Creator<SavedState>() {\n            @Override\n            public SavedState createFromParcel(Parcel source) {\n                return new SavedState(source);\n            }\n\n            @Override\n            public SavedState[] newArray(int size) {\n                return new SavedState[size];\n            }\n        };\n\n        @Override\n        @NonNull\n        public String toString() {\n            return \"SavedState{\" +\n                    \"mAnchorPosition=\" + mAnchorPosition +\n                    \", mAnchorOffset=\" + mAnchorOffset +\n                    '}';\n        }\n    }\n}\n"
  },
  {
    "path": "flexbox/src/main/java/com/google/android/flexbox/JustifyContent.java",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage com.google.android.flexbox;\n\nimport java.lang.annotation.Retention;\nimport java.lang.annotation.RetentionPolicy;\n\nimport androidx.annotation.IntDef;\n\n/** This attribute controls the alignment along the main axis. */\n@IntDef({JustifyContent.FLEX_START, JustifyContent.FLEX_END, JustifyContent.CENTER,\n        JustifyContent.SPACE_BETWEEN, JustifyContent.SPACE_AROUND, JustifyContent.SPACE_EVENLY})\n@Retention(RetentionPolicy.SOURCE)\npublic @interface JustifyContent {\n\n    /** Flex items are packed toward the start line. */\n    int FLEX_START = 0;\n\n    /** Flex items are packed toward the end line. */\n    int FLEX_END = 1;\n\n    /** Flex items are centered along the flex line where the flex items belong. */\n    int CENTER = 2;\n\n    /**\n     * Flex items are evenly distributed along the flex line, first flex item is on the\n     * start line, the last flex item is on the end line.\n     */\n    int SPACE_BETWEEN = 3;\n\n    /**\n     * Flex items are evenly distributed along the flex line with the same amount of spaces between\n     * the flex lines.\n     */\n    int SPACE_AROUND = 4;\n\n    /**\n     * Flex items are evenly distributed along the flex line. The difference between\n     * {@link #SPACE_AROUND} is that all the spaces between items should be the same as the\n     * space before the first item and after the last item.\n     * See\n     * <a href=\"https://developer.mozilla.org/en-US/docs/Web/CSS/justify-content\">the document on MDN</a>\n     * for more details.\n     */\n    int SPACE_EVENLY = 5;\n}\n"
  },
  {
    "path": "flexbox/src/main/res/values/attrs.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?><!--\nCopyright 2016 Google Inc. All rights reserved.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this file except in compliance with the License.\nYou may obtain a copy of the License at\n\n     http://www.apache.org/licenses/LICENSE-2.0\n\nUnless required by applicable law or agreed to in writing, software\ndistributed under the License is distributed on an \"AS IS\" BASIS,\nWITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\nSee the License for the specific language governing permissions and\nlimitations under the License.\n-->\n<resources>\n    <declare-styleable name=\"FlexboxLayout\">\n        <attr name=\"flexDirection\">\n            <enum name=\"row\" value=\"0\" />\n            <enum name=\"row_reverse\" value=\"1\" />\n            <enum name=\"column\" value=\"2\" />\n            <enum name=\"column_reverse\" value=\"3\" />\n        </attr>\n\n        <attr name=\"flexWrap\">\n            <enum name=\"nowrap\" value=\"0\" />\n            <enum name=\"wrap\" value=\"1\" />\n            <enum name=\"wrap_reverse\" value=\"2\" />\n        </attr>\n\n        <!--\n            Omitting flex-flow property since it's reflected in the parent flex container.\n            Set the flexDirection and/or flexWrap to the parent flex container explicitly if you\n            want to use the flex-flow similar way to the web.\n         -->\n\n        <attr name=\"justifyContent\">\n            <enum name=\"flex_start\" value=\"0\" />\n            <enum name=\"flex_end\" value=\"1\" />\n            <enum name=\"center\" value=\"2\" />\n            <enum name=\"space_between\" value=\"3\" />\n            <enum name=\"space_around\" value=\"4\" />\n            <enum name=\"space_evenly\" value=\"5\" />\n        </attr>\n\n        <attr name=\"alignItems\">\n            <enum name=\"flex_start\" value=\"0\" />\n            <enum name=\"flex_end\" value=\"1\" />\n            <enum name=\"center\" value=\"2\" />\n            <enum name=\"baseline\" value=\"3\" />\n            <enum name=\"stretch\" value=\"4\" />\n        </attr>\n\n        <attr name=\"alignContent\">\n            <enum name=\"flex_start\" value=\"0\" />\n            <enum name=\"flex_end\" value=\"1\" />\n            <enum name=\"center\" value=\"2\" />\n            <enum name=\"space_between\" value=\"3\" />\n            <enum name=\"space_around\" value=\"4\" />\n            <enum name=\"stretch\" value=\"5\" />\n        </attr>\n\n        <attr name=\"dividerDrawable\" format=\"reference\" />\n        <attr name=\"dividerDrawableHorizontal\" format=\"reference\" />\n        <attr name=\"dividerDrawableVertical\" format=\"reference\" />\n\n        <attr name=\"showDivider\">\n            <flag name=\"none\" value=\"0\" />\n            <flag name=\"beginning\" value=\"1\" />\n            <flag name=\"middle\" value=\"2\" />\n            <flag name=\"end\" value=\"4\" />\n        </attr>\n        <attr name=\"showDividerHorizontal\">\n            <flag name=\"none\" value=\"0\" />\n            <flag name=\"beginning\" value=\"1\" />\n            <flag name=\"middle\" value=\"2\" />\n            <flag name=\"end\" value=\"4\" />\n        </attr>\n        <attr name=\"showDividerVertical\">\n            <flag name=\"none\" value=\"0\" />\n            <flag name=\"beginning\" value=\"1\" />\n            <flag name=\"middle\" value=\"2\" />\n            <flag name=\"end\" value=\"4\" />\n        </attr>\n\n        <!--\n            The attribute that specifies the maximum number of flex lines. This attribute is\n            effective only when the flexWrap attribute is \"wrap\" or \"wrap_reverse\".\n        -->\n        <attr name=\"maxLine\" format=\"integer\" />\n\n    </declare-styleable>\n\n    <declare-styleable name=\"FlexboxLayout_Layout\">\n        <attr name=\"layout_order\" format=\"integer\" />\n\n        <!-- Negative numbers are invalid. -->\n        <attr name=\"layout_flexGrow\" format=\"float\" />\n\n        <!-- Negative numbers are invalid. -->\n        <attr name=\"layout_flexShrink\" format=\"float\" />\n\n        <!--\n            The initial length in a percentage format relative to its parent. This is similar to the\n            flex-basis property in the original CSS specification.\n            (https://www.w3.org/TR/css-flexbox-1/#flex-basis-property)\n            But unlike the flex-basis property, this attribute only accepts a value in fraction\n            (percentage), whereas flex-basis property accepts width values such as 1em, 10px and\n            the 'content' string.\n            But specifying initial fixed width values can be done by specifying width values in\n            layout_width (or layout_height, varies depending on the flexDirection). Also the same\n            effect can be done by specifying \"wrap_content\" in layout_width (or layout_height) if\n            developers want to achieve the same effect as 'content'.\n            Thus, this attribute only accepts fraction values, which can't be done through\n            layout_width (or layout_height) for simplicity.\n        -->\n        <attr name=\"layout_flexBasisPercent\" format=\"fraction\" />\n\n        <!--\n            Omitting flex property since it's a shorthand for layout_flexGrow and layout_flexShrink\n            and layout_percentInParent (flex-basis in the original CSS spec).\n        -->\n\n        <attr name=\"layout_alignSelf\">\n            <enum name=\"auto\" value=\"-1\" />\n            <!-- The values below need to match the values of alignItems -->\n            <enum name=\"flex_start\" value=\"0\" />\n            <enum name=\"flex_end\" value=\"1\" />\n            <enum name=\"center\" value=\"2\" />\n            <enum name=\"baseline\" value=\"3\" />\n            <enum name=\"stretch\" value=\"4\" />\n        </attr>\n\n        <attr name=\"layout_minWidth\" format=\"dimension\" />\n        <attr name=\"layout_minHeight\" format=\"dimension\" />\n        <attr name=\"layout_maxWidth\" format=\"dimension\" />\n        <attr name=\"layout_maxHeight\" format=\"dimension\" />\n\n        <!--\n            This attribute forces a flex line wrapping. i.e. if this is set to true for a\n            flex item, the item will become the first item of a flex line. (A wrapping happens\n            regardless of the flex items being processed in the the previous flex line)\n            This attribute is ignored if the flex_wrap attribute is set to nowrap.\n            The equivalent attribute isn't defined in the original CSS Flexible Box Module\n            specification, but having this attribute is useful for Android developers to flatten\n            the layouts when building a grid like layout or for a situation where developers want\n            to put a new flex line to make a semantic difference from the previous one, etc.\n        -->\n        <attr name=\"layout_wrapBefore\" format=\"boolean\" />\n    </declare-styleable>\n</resources>"
  },
  {
    "path": "gradle/wrapper/gradle-wrapper.properties",
    "content": "#Mon Sep 09 14:42:19 PDT 2019\ndistributionBase=GRADLE_USER_HOME\ndistributionPath=wrapper/dists\nzipStoreBase=GRADLE_USER_HOME\nzipStorePath=wrapper/dists\ndistributionUrl=https\\://services.gradle.org/distributions/gradle-6.7.1-all.zip\n"
  },
  {
    "path": "gradle.properties",
    "content": "#\n# Copyright 2016 Google Inc. All rights reserved.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n#      http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n#\n\n# Project-wide Gradle settings.\n\n# IDE (e.g. Android Studio) users:\n# Gradle settings configured through the IDE *will override*\n# any settings specified in this file.\n\n# For more details on how to configure your build environment visit\n# http://www.gradle.org/docs/current/userguide/build_environment.html\n\n# Specifies the JVM arguments used for the daemon process.\n# The setting is particularly useful for tweaking memory settings.\n# Default value: -Xmx10248m -XX:MaxPermSize=256m\n# org.gradle.jvmargs=-Xmx2048m -XX:MaxPermSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8\n\n# When configured, Gradle will run in incubating parallel mode.\n# This option should only be used with decoupled projects. More details, visit\n# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects\n# org.gradle.parallel=true\n\nandroid.enableJetifier=true\nandroid.useAndroidX=true"
  },
  {
    "path": "gradlew",
    "content": "#!/usr/bin/env sh\n\n##############################################################################\n##\n##  Gradle start up script for UN*X\n##\n##############################################################################\n\n# Attempt to set APP_HOME\n# Resolve links: $0 may be a link\nPRG=\"$0\"\n# Need this for relative symlinks.\nwhile [ -h \"$PRG\" ] ; do\n    ls=`ls -ld \"$PRG\"`\n    link=`expr \"$ls\" : '.*-> \\(.*\\)$'`\n    if expr \"$link\" : '/.*' > /dev/null; then\n        PRG=\"$link\"\n    else\n        PRG=`dirname \"$PRG\"`\"/$link\"\n    fi\ndone\nSAVED=\"`pwd`\"\ncd \"`dirname \\\"$PRG\\\"`/\" >/dev/null\nAPP_HOME=\"`pwd -P`\"\ncd \"$SAVED\" >/dev/null\n\nAPP_NAME=\"Gradle\"\nAPP_BASE_NAME=`basename \"$0\"`\n\n# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.\nDEFAULT_JVM_OPTS=\"\"\n\n# Use the maximum available, or set MAX_FD != -1 to use that value.\nMAX_FD=\"maximum\"\n\nwarn () {\n    echo \"$*\"\n}\n\ndie () {\n    echo\n    echo \"$*\"\n    echo\n    exit 1\n}\n\n# OS specific support (must be 'true' or 'false').\ncygwin=false\nmsys=false\ndarwin=false\nnonstop=false\ncase \"`uname`\" in\n  CYGWIN* )\n    cygwin=true\n    ;;\n  Darwin* )\n    darwin=true\n    ;;\n  MINGW* )\n    msys=true\n    ;;\n  NONSTOP* )\n    nonstop=true\n    ;;\nesac\n\nCLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar\n\n# Determine the Java command to use to start the JVM.\nif [ -n \"$JAVA_HOME\" ] ; then\n    if [ -x \"$JAVA_HOME/jre/sh/java\" ] ; then\n        # IBM's JDK on AIX uses strange locations for the executables\n        JAVACMD=\"$JAVA_HOME/jre/sh/java\"\n    else\n        JAVACMD=\"$JAVA_HOME/bin/java\"\n    fi\n    if [ ! -x \"$JAVACMD\" ] ; then\n        die \"ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME\n\nPlease set the JAVA_HOME variable in your environment to match the\nlocation of your Java installation.\"\n    fi\nelse\n    JAVACMD=\"java\"\n    which java >/dev/null 2>&1 || die \"ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.\n\nPlease set the JAVA_HOME variable in your environment to match the\nlocation of your Java installation.\"\nfi\n\n# Increase the maximum file descriptors if we can.\nif [ \"$cygwin\" = \"false\" -a \"$darwin\" = \"false\" -a \"$nonstop\" = \"false\" ] ; then\n    MAX_FD_LIMIT=`ulimit -H -n`\n    if [ $? -eq 0 ] ; then\n        if [ \"$MAX_FD\" = \"maximum\" -o \"$MAX_FD\" = \"max\" ] ; then\n            MAX_FD=\"$MAX_FD_LIMIT\"\n        fi\n        ulimit -n $MAX_FD\n        if [ $? -ne 0 ] ; then\n            warn \"Could not set maximum file descriptor limit: $MAX_FD\"\n        fi\n    else\n        warn \"Could not query maximum file descriptor limit: $MAX_FD_LIMIT\"\n    fi\nfi\n\n# For Darwin, add options to specify how the application appears in the dock\nif $darwin; then\n    GRADLE_OPTS=\"$GRADLE_OPTS \\\"-Xdock:name=$APP_NAME\\\" \\\"-Xdock:icon=$APP_HOME/media/gradle.icns\\\"\"\nfi\n\n# For Cygwin, switch paths to Windows format before running java\nif $cygwin ; then\n    APP_HOME=`cygpath --path --mixed \"$APP_HOME\"`\n    CLASSPATH=`cygpath --path --mixed \"$CLASSPATH\"`\n    JAVACMD=`cygpath --unix \"$JAVACMD\"`\n\n    # We build the pattern for arguments to be converted via cygpath\n    ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`\n    SEP=\"\"\n    for dir in $ROOTDIRSRAW ; do\n        ROOTDIRS=\"$ROOTDIRS$SEP$dir\"\n        SEP=\"|\"\n    done\n    OURCYGPATTERN=\"(^($ROOTDIRS))\"\n    # Add a user-defined pattern to the cygpath arguments\n    if [ \"$GRADLE_CYGPATTERN\" != \"\" ] ; then\n        OURCYGPATTERN=\"$OURCYGPATTERN|($GRADLE_CYGPATTERN)\"\n    fi\n    # Now convert the arguments - kludge to limit ourselves to /bin/sh\n    i=0\n    for arg in \"$@\" ; do\n        CHECK=`echo \"$arg\"|egrep -c \"$OURCYGPATTERN\" -`\n        CHECK2=`echo \"$arg\"|egrep -c \"^-\"`                                 ### Determine if an option\n\n        if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then                    ### Added a condition\n            eval `echo args$i`=`cygpath --path --ignore --mixed \"$arg\"`\n        else\n            eval `echo args$i`=\"\\\"$arg\\\"\"\n        fi\n        i=$((i+1))\n    done\n    case $i in\n        (0) set -- ;;\n        (1) set -- \"$args0\" ;;\n        (2) set -- \"$args0\" \"$args1\" ;;\n        (3) set -- \"$args0\" \"$args1\" \"$args2\" ;;\n        (4) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" ;;\n        (5) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" ;;\n        (6) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" \"$args5\" ;;\n        (7) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" \"$args5\" \"$args6\" ;;\n        (8) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" \"$args5\" \"$args6\" \"$args7\" ;;\n        (9) set -- \"$args0\" \"$args1\" \"$args2\" \"$args3\" \"$args4\" \"$args5\" \"$args6\" \"$args7\" \"$args8\" ;;\n    esac\nfi\n\n# Escape application args\nsave () {\n    for i do printf %s\\\\n \"$i\" | sed \"s/'/'\\\\\\\\''/g;1s/^/'/;\\$s/\\$/' \\\\\\\\/\" ; done\n    echo \" \"\n}\nAPP_ARGS=$(save \"$@\")\n\n# Collect all arguments for the java command, following the shell quoting and substitution rules\neval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS \"\\\"-Dorg.gradle.appname=$APP_BASE_NAME\\\"\" -classpath \"\\\"$CLASSPATH\\\"\" org.gradle.wrapper.GradleWrapperMain \"$APP_ARGS\"\n\n# by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong\nif [ \"$(uname)\" = \"Darwin\" ] && [ \"$HOME\" = \"$PWD\" ]; then\n  cd \"$(dirname \"$0\")\"\nfi\n\nexec \"$JAVACMD\" \"$@\"\n"
  },
  {
    "path": "gradlew.bat",
    "content": "@if \"%DEBUG%\" == \"\" @echo off\r\n@rem ##########################################################################\r\n@rem\r\n@rem  Gradle startup script for Windows\r\n@rem\r\n@rem ##########################################################################\r\n\r\n@rem Set local scope for the variables with windows NT shell\r\nif \"%OS%\"==\"Windows_NT\" setlocal\r\n\r\nset DIRNAME=%~dp0\r\nif \"%DIRNAME%\" == \"\" set DIRNAME=.\r\nset APP_BASE_NAME=%~n0\r\nset APP_HOME=%DIRNAME%\r\n\r\n@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.\r\nset DEFAULT_JVM_OPTS=\r\n\r\n@rem Find java.exe\r\nif defined JAVA_HOME goto findJavaFromJavaHome\r\n\r\nset JAVA_EXE=java.exe\r\n%JAVA_EXE% -version >NUL 2>&1\r\nif \"%ERRORLEVEL%\" == \"0\" goto init\r\n\r\necho.\r\necho ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.\r\necho.\r\necho Please set the JAVA_HOME variable in your environment to match the\r\necho location of your Java installation.\r\n\r\ngoto fail\r\n\r\n:findJavaFromJavaHome\r\nset JAVA_HOME=%JAVA_HOME:\"=%\r\nset JAVA_EXE=%JAVA_HOME%/bin/java.exe\r\n\r\nif exist \"%JAVA_EXE%\" goto init\r\n\r\necho.\r\necho ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%\r\necho.\r\necho Please set the JAVA_HOME variable in your environment to match the\r\necho location of your Java installation.\r\n\r\ngoto fail\r\n\r\n:init\r\n@rem Get command-line arguments, handling Windows variants\r\n\r\nif not \"%OS%\" == \"Windows_NT\" goto win9xME_args\r\n\r\n:win9xME_args\r\n@rem Slurp the command line arguments.\r\nset CMD_LINE_ARGS=\r\nset _SKIP=2\r\n\r\n:win9xME_args_slurp\r\nif \"x%~1\" == \"x\" goto execute\r\n\r\nset CMD_LINE_ARGS=%*\r\n\r\n:execute\r\n@rem Setup the command line\r\n\r\nset CLASSPATH=%APP_HOME%\\gradle\\wrapper\\gradle-wrapper.jar\r\n\r\n@rem Execute Gradle\r\n\"%JAVA_EXE%\" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% \"-Dorg.gradle.appname=%APP_BASE_NAME%\" -classpath \"%CLASSPATH%\" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%\r\n\r\n:end\r\n@rem End local scope for the variables with windows NT shell\r\nif \"%ERRORLEVEL%\"==\"0\" goto mainEnd\r\n\r\n:fail\r\nrem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of\r\nrem the _cmd.exe /c_ return code!\r\nif  not \"\" == \"%GRADLE_EXIT_CONSOLE%\" exit 1\r\nexit /b 1\r\n\r\n:mainEnd\r\nif \"%OS%\"==\"Windows_NT\" endlocal\r\n\r\n:omega\r\n"
  },
  {
    "path": "settings.gradle",
    "content": "/*\n * Copyright 2016 Google Inc. All rights reserved.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *      http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\ninclude ':demo-playground', ':demo-cat-gallery', ':flexbox'\n"
  },
  {
    "path": "tool/codeStyleSettings.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"ProjectCodeStyleSettingsManager\">\n    <option name=\"PER_PROJECT_SETTINGS\">\n      <value>\n        <option name=\"FIELD_NAME_PREFIX\" value=\"m\" />\n        <option name=\"STATIC_FIELD_NAME_PREFIX\" value=\"s\" />\n        <option name=\"CLASS_COUNT_TO_USE_IMPORT_ON_DEMAND\" value=\"9999\" />\n        <option name=\"NAMES_COUNT_TO_USE_IMPORT_ON_DEMAND\" value=\"9999\" />\n        <option name=\"IMPORT_LAYOUT_TABLE\">\n          <value>\n            <package name=\"android\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"com.android\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"dalvik\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"libcore\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"com\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"gov\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"junit\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"net\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"org\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"java\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"javax\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"\" withSubpackages=\"true\" static=\"true\" />\n            <emptyLine />\n            <package name=\"android\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"com.android\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"dalvik\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"libcore\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"com\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"gov\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"junit\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"net\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"org\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"java\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"javax\" withSubpackages=\"true\" static=\"false\" />\n            <emptyLine />\n            <package name=\"\" withSubpackages=\"true\" static=\"false\" />\n          </value>\n        </option>\n        <option name=\"RIGHT_MARGIN\" value=\"100\" />\n        <option name=\"JD_P_AT_EMPTY_LINES\" value=\"false\" />\n        <option name=\"JD_DO_NOT_WRAP_ONE_LINE_COMMENTS\" value=\"true\" />\n        <option name=\"JD_KEEP_EMPTY_PARAMETER\" value=\"false\" />\n        <option name=\"JD_KEEP_EMPTY_EXCEPTION\" value=\"false\" />\n        <option name=\"JD_KEEP_EMPTY_RETURN\" value=\"false\" />\n        <option name=\"JD_PRESERVE_LINE_FEEDS\" value=\"true\" />\n        <option name=\"KEEP_CONTROL_STATEMENT_IN_ONE_LINE\" value=\"false\" />\n        <option name=\"KEEP_BLANK_LINES_IN_CODE\" value=\"1\" />\n        <option name=\"BLANK_LINES_AROUND_FIELD\" value=\"1\" />\n        <option name=\"BLANK_LINES_AFTER_CLASS_HEADER\" value=\"1\" />\n        <option name=\"ALIGN_MULTILINE_PARAMETERS\" value=\"false\" />\n        <option name=\"ALIGN_MULTILINE_FOR\" value=\"false\" />\n        <option name=\"CALL_PARAMETERS_WRAP\" value=\"1\" />\n        <option name=\"METHOD_PARAMETERS_WRAP\" value=\"1\" />\n        <option name=\"EXTENDS_LIST_WRAP\" value=\"1\" />\n        <option name=\"THROWS_LIST_WRAP\" value=\"1\" />\n        <option name=\"EXTENDS_KEYWORD_WRAP\" value=\"1\" />\n        <option name=\"THROWS_KEYWORD_WRAP\" value=\"1\" />\n        <option name=\"METHOD_CALL_CHAIN_WRAP\" value=\"1\" />\n        <option name=\"BINARY_OPERATION_WRAP\" value=\"1\" />\n        <option name=\"BINARY_OPERATION_SIGN_ON_NEXT_LINE\" value=\"true\" />\n        <option name=\"TERNARY_OPERATION_WRAP\" value=\"1\" />\n        <option name=\"TERNARY_OPERATION_SIGNS_ON_NEXT_LINE\" value=\"true\" />\n        <option name=\"FOR_STATEMENT_WRAP\" value=\"1\" />\n        <option name=\"ARRAY_INITIALIZER_WRAP\" value=\"1\" />\n        <option name=\"ASSIGNMENT_WRAP\" value=\"1\" />\n        <option name=\"PLACE_ASSIGNMENT_SIGN_ON_NEXT_LINE\" value=\"true\" />\n        <option name=\"WRAP_COMMENTS\" value=\"true\" />\n        <option name=\"IF_BRACE_FORCE\" value=\"3\" />\n        <option name=\"DOWHILE_BRACE_FORCE\" value=\"3\" />\n        <option name=\"WHILE_BRACE_FORCE\" value=\"3\" />\n        <option name=\"FOR_BRACE_FORCE\" value=\"3\" />\n        <Objective-C-extensions>\n          <option name=\"GENERATE_INSTANCE_VARIABLES_FOR_PROPERTIES\" value=\"ASK\" />\n          <option name=\"RELEASE_STYLE\" value=\"IVAR\" />\n          <option name=\"TYPE_QUALIFIERS_PLACEMENT\" value=\"BEFORE\" />\n          <file>\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Import\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Macro\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Typedef\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Enum\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Constant\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Global\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Struct\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"FunctionPredecl\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Function\" />\n          </file>\n          <class>\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Property\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"Synthesize\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"InitMethod\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"StaticMethod\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"InstanceMethod\" />\n            <option name=\"com.jetbrains.cidr.lang.util.OCDeclarationKind\" value=\"DeallocMethod\" />\n          </class>\n          <extensions>\n            <pair source=\"cpp\" header=\"h\" />\n            <pair source=\"c\" header=\"h\" />\n          </extensions>\n        </Objective-C-extensions>\n        <XML>\n          <option name=\"XML_LEGACY_SETTINGS_IMPORTED\" value=\"true\" />\n        </XML>\n        <ADDITIONAL_INDENT_OPTIONS fileType=\"java\">\n          <option name=\"TAB_SIZE\" value=\"8\" />\n        </ADDITIONAL_INDENT_OPTIONS>\n        <ADDITIONAL_INDENT_OPTIONS fileType=\"js\">\n          <option name=\"CONTINUATION_INDENT_SIZE\" value=\"4\" />\n        </ADDITIONAL_INDENT_OPTIONS>\n        <codeStyleSettings language=\"JAVA\">\n          <option name=\"ALIGN_MULTILINE_PARAMETERS\" value=\"false\" />\n          <option name=\"ALIGN_MULTILINE_FOR\" value=\"false\" />\n          <option name=\"CALL_PARAMETERS_WRAP\" value=\"1\" />\n          <option name=\"PREFER_PARAMETERS_WRAP\" value=\"true\" />\n          <option name=\"METHOD_PARAMETERS_WRAP\" value=\"1\" />\n          <option name=\"RESOURCE_LIST_WRAP\" value=\"1\" />\n          <option name=\"EXTENDS_LIST_WRAP\" value=\"1\" />\n          <option name=\"THROWS_LIST_WRAP\" value=\"1\" />\n          <option name=\"THROWS_KEYWORD_WRAP\" value=\"1\" />\n          <option name=\"BINARY_OPERATION_WRAP\" value=\"1\" />\n          <option name=\"BINARY_OPERATION_SIGN_ON_NEXT_LINE\" value=\"true\" />\n          <option name=\"TERNARY_OPERATION_WRAP\" value=\"1\" />\n          <option name=\"TERNARY_OPERATION_SIGNS_ON_NEXT_LINE\" value=\"true\" />\n          <option name=\"FOR_STATEMENT_WRAP\" value=\"1\" />\n          <option name=\"ARRAY_INITIALIZER_WRAP\" value=\"1\" />\n          <option name=\"ASSIGNMENT_WRAP\" value=\"1\" />\n          <option name=\"IF_BRACE_FORCE\" value=\"1\" />\n          <option name=\"DOWHILE_BRACE_FORCE\" value=\"1\" />\n          <option name=\"WHILE_BRACE_FORCE\" value=\"1\" />\n          <option name=\"FOR_BRACE_FORCE\" value=\"1\" />\n          <option name=\"WRAP_LONG_LINES\" value=\"true\" />\n        </codeStyleSettings>\n        <codeStyleSettings language=\"XML\">\n          <option name=\"FORCE_REARRANGE_MODE\" value=\"1\" />\n          <indentOptions>\n            <option name=\"CONTINUATION_INDENT_SIZE\" value=\"4\" />\n          </indentOptions>\n          <arrangement>\n            <rules>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>xmlns:android</NAME>\n                      <XML_NAMESPACE>^$</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>xmlns:.*</NAME>\n                      <XML_NAMESPACE>^$</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                  <order>BY_NAME</order>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*:id</NAME>\n                      <XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*:name</NAME>\n                      <XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>name</NAME>\n                      <XML_NAMESPACE>^$</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>style</NAME>\n                      <XML_NAMESPACE>^$</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*</NAME>\n                      <XML_NAMESPACE>^$</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                  <order>BY_NAME</order>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*:layout_width</NAME>\n                      <XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*:layout_height</NAME>\n                      <XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*:layout_.*</NAME>\n                      <XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                  <order>BY_NAME</order>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*:width</NAME>\n                      <XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                  <order>BY_NAME</order>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*:height</NAME>\n                      <XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                  <order>BY_NAME</order>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*</NAME>\n                      <XML_NAMESPACE>http://schemas.android.com/apk/res/android</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                  <order>BY_NAME</order>\n                </rule>\n              </section>\n              <section>\n                <rule>\n                  <match>\n                    <AND>\n                      <NAME>.*</NAME>\n                      <XML_NAMESPACE>.*</XML_NAMESPACE>\n                    </AND>\n                  </match>\n                  <order>BY_NAME</order>\n                </rule>\n              </section>\n            </rules>\n          </arrangement>\n        </codeStyleSettings>\n      </value>\n    </option>\n    <option name=\"USE_PER_PROJECT_SETTINGS\" value=\"true\" />\n    <option name=\"PREFERRED_PROJECT_CODE_STYLE\" value=\"AndroidStyle\" />\n  </component>\n</project>"
  }
]