// Signature format: 4.0
package com.google.accompanist.flowlayout {

  @Deprecated public enum FlowCrossAxisAlignment {
    method @Deprecated public static com.google.accompanist.flowlayout.FlowCrossAxisAlignment valueOf(String name) throws java.lang.IllegalArgumentException;
    method @Deprecated public static com.google.accompanist.flowlayout.FlowCrossAxisAlignment[] values();
    enum_constant @Deprecated public static final com.google.accompanist.flowlayout.FlowCrossAxisAlignment Center;
    enum_constant @Deprecated public static final com.google.accompanist.flowlayout.FlowCrossAxisAlignment End;
    enum_constant @Deprecated public static final com.google.accompanist.flowlayout.FlowCrossAxisAlignment Start;
  }

  public final class FlowKt {
    method @Deprecated @androidx.compose.runtime.Composable public static void FlowColumn(optional androidx.compose.ui.Modifier modifier, optional com.google.accompanist.flowlayout.SizeMode mainAxisSize, optional com.google.accompanist.flowlayout.MainAxisAlignment mainAxisAlignment, optional float mainAxisSpacing, optional com.google.accompanist.flowlayout.FlowCrossAxisAlignment crossAxisAlignment, optional float crossAxisSpacing, optional com.google.accompanist.flowlayout.MainAxisAlignment lastLineMainAxisAlignment, kotlin.jvm.functions.Function0<kotlin.Unit> content);
    method @Deprecated @androidx.compose.runtime.Composable public static void FlowRow(optional androidx.compose.ui.Modifier modifier, optional com.google.accompanist.flowlayout.SizeMode mainAxisSize, optional com.google.accompanist.flowlayout.MainAxisAlignment mainAxisAlignment, optional float mainAxisSpacing, optional com.google.accompanist.flowlayout.FlowCrossAxisAlignment crossAxisAlignment, optional float crossAxisSpacing, optional com.google.accompanist.flowlayout.MainAxisAlignment lastLineMainAxisAlignment, kotlin.jvm.functions.Function0<kotlin.Unit> content);
  }

  public enum MainAxisAlignment {
    method public static com.google.accompanist.flowlayout.MainAxisAlignment valueOf(String name) throws java.lang.IllegalArgumentException;
    method public static com.google.accompanist.flowlayout.MainAxisAlignment[] values();
    enum_constant public static final com.google.accompanist.flowlayout.MainAxisAlignment Center;
    enum_constant public static final com.google.accompanist.flowlayout.MainAxisAlignment End;
    enum_constant public static final com.google.accompanist.flowlayout.MainAxisAlignment SpaceAround;
    enum_constant public static final com.google.accompanist.flowlayout.MainAxisAlignment SpaceBetween;
    enum_constant public static final com.google.accompanist.flowlayout.MainAxisAlignment SpaceEvenly;
    enum_constant public static final com.google.accompanist.flowlayout.MainAxisAlignment Start;
  }

  @Deprecated public enum SizeMode {
    method @Deprecated public static com.google.accompanist.flowlayout.SizeMode valueOf(String name) throws java.lang.IllegalArgumentException;
    method @Deprecated public static com.google.accompanist.flowlayout.SizeMode[] values();
    enum_constant @Deprecated public static final com.google.accompanist.flowlayout.SizeMode Expand;
    enum_constant @Deprecated public static final com.google.accompanist.flowlayout.SizeMode Wrap;
  }

}

