【问题标题】:Outlined Textbox in Xamarin.FormsXamarin.Forms 中的大纲文本框
【发布时间】:2020-03-26 16:49:37
【问题描述】:

我想在 Xamarin.Forms 中实现材料概述文本框。我创建了自定义渲染器,但无法对其应用样式。 我想要这样的文本框https://i.stack.imgur.com/7pWPr.png

通过创建自定义渲染器并从 TextInputLayout 继承显示默认材质文本框。 https://i.stack.imgur.com/Ek9Vb.jpg

【问题讨论】:

  • 自定义渲染器是一个选项,但您也可以使用 Grid、Boxview(或 Frame)、Label、Entry 和一些想象力来实现。
  • @SaiyamShah 嗨,如果你想自定义一个EntryRenderer 来使用Material Design Text Input Layout,那将是不可能的。因为 Xamarin 表单的 EntryRenderer 继承自 Android 中的 EditText。因此,如果使用Renderer来实现,应该使用ViewRenderer

标签: xamarin xamarin.forms material-design custom-renderer


【解决方案1】:

您可以使用Custom Renderer 自定义包含设计为Entry 的材质的视图。

在表单中创建一个EntryView

public class EntryView : ContentView
{
    public static readonly BindableProperty TextProperty =
      BindableProperty.Create("Text", typeof(string), typeof(EntryView), null);
    public string Text
    {
        get { return (string)GetValue(TextProperty); }
        set { SetValue(TextProperty, value); }
    }
}

其次,你需要在Android中创建EntryViewRenderer

public class EntryViewRenderer : ViewRenderer
{
    global::Android.Views.View view;
    global::Android.Widget.EditText editText;
    EntryView entryView;
    Activity activity;

    protected override void OnElementChanged(ElementChangedEventArgs<Xamarin.Forms.View> e)
    {
        base.OnElementChanged(e);
        if(e.NewElement != null)
        {
            entryView= e.NewElement as EntryView;
        }

        if (e.OldElement != null || Element == null)
        {
            return;
        }

        try
        {
            SetupUserInterface();
            SetupEventHandlers();
            AddView(view);
        }
        catch (Exception ex)
        {
            System.Diagnostics.Debug.WriteLine(@"           ERROR: ", ex.Message);
        }
    }

    private void SetupEventHandlers()
    {
        editText.TextChanged += EditText_TextChanged;
    }

    private void EditText_TextChanged(object sender, Android.Text.TextChangedEventArgs e)
    {
        entryView.Text = editText.Text; 
        Console.WriteLine("chanegd +" + entryView.Text);
    }

    void SetupUserInterface()
    {
        activity = this.Context as Activity;
        view = activity.LayoutInflater.Inflate(Resource.Layout.EntryLayout, this, false);

        editText = view.FindViewById<EditText>(Resource.Id.editText1);
    }

    protected override void OnLayout(bool changed, int l, int t, int r, int b)
    {
        base.OnLayout(changed, l, t, r, b);

        var msw = MeasureSpec.MakeMeasureSpec(r - l, MeasureSpecMode.Exactly);
        var msh = MeasureSpec.MakeMeasureSpec(b - t, MeasureSpecMode.Exactly);

        view.Measure(msw, msh);
        view.Layout(0, 0, r - l, b - t);
    }
}

另外,你需要为这个View添加EntryLayout

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <android.support.design.widget.TextInputLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        style="@style/Widget.MaterialComponents.TextInputLayout.OutlinedBox">
        <EditText
            android:id="@+id/editText1"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:hint="Label"
            android:outlineSpotShadowColor="@color/cardview_shadow_start_color"/>
    </android.support.design.widget.TextInputLayout>

</LinearLayout>

现在,您可以在 Xamarin Forms 的 Xaml 中使用它:

xmlns:app18="clr-namespace:App18"

<app18:EntryView Text="abc"/>

效果:

如果需要修改轮廓颜色,只需在Resources/values/styles.xml中添加style即可。

  <style name="LoginTextInputLayoutStyle" parent="Widget.MaterialComponents.TextInputLayout.OutlinedBox.Dense">
    <item name="boxStrokeColor">#570dff</item>
    <item name="boxStrokeWidth">2dp</item>
    <item name="android:textColorHint">#570dff</item>
  </style>

Resources/values/colors.xml 中添加以下代码:

<color name="mtrl_textinput_default_box_stroke_color">#570dff</color>

终于用在EntryLayout.xml

<android.support.design.widget.TextInputLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    style="@style/LoginTextInputLayoutStyle">
    <EditText
        android:id="@+id/editText1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="Label"/>
</android.support.design.widget.TextInputLayout>

效果:

【讨论】:

  • 这是我需要的。非常感谢,我试试看。
  • 我已经尝试过您的解决方案,但我遇到了一些错误。我正在发布我的解决方案链接github.com/saiyamshah143/MaterialEntry。它也有我面临的错误截图。
  • @SaiyamShah Okey,我会检查的。
  • @SaiyamShah 在共享代码中,我只是修改了这一行:&lt;app18:EntryView WidthRequest="200" HeightRequest="50"/&gt; 它可以工作。
  • 它工作正常,但仍不如预期 - prntscr.com/qiu2l5
【解决方案2】:

您可以使用带有一些 -ve 边距值的 Grid 来实现,如下所示:

<Grid>
    <Frame Padding="10"
            BorderColor="#570dff"
            HasShadow="False">
        <Entry Placeholder="Enter here"/>
    </Frame>
    <Label Text=" UserName "
            FontSize="15"
            TextColor="#570dff"
            BackgroundColor="white"
            HorizontalOptions="Start"
            VerticalOptions="Start"
            Margin="20,-10,0,0"/>
</Grid>

输出:

【讨论】:

  • 其实我可以用Grid,但是我想用Material Design Text Input Layout。即 Widget.MaterialComponents.TextInputLayout.OutlinedBox.Dense 我创建了自定义渲染器,但无法应用样式以编程方式进行控制。
【解决方案3】:
<Grid Margin="20">
    <Frame  Padding="10"
            BorderColor="#570dff"
            HasShadow="False">
        <Entry Placeholder="Enter here"/>
    </Frame>
    <Label  Text=" UserName "
            FontSize="15"
            TextColor="#570dff"
            BackgroundColor="white"
            HorizontalOptions="Start"
            VerticalOptions="Start"
            Margin="20,-10,0,0"/>
</Grid>

这很好,它也帮助了我。我在网格中添加了 20 的边距以使其看起来更好。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-08-20
    • 2014-08-09
    • 2011-03-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多