无法在具有多个实例的片段中设置属性

时间:2016-08-25 20:09:20

标签: c# android android-fragments xamarin android-viewpager

我有一个主要活动,里面有一个ViewPager。 ViewPager使用FragmentPagerAdapter将Fragments放入ViewPager。所有片段都是一个PdfAssetFragment,它包含一个PDFView(Joan Zapata)和我写的自定义视图,名为DrawingView(允许用户在屏幕上绘图)。当我调用更改当前页面中的DrawingView的属性时(ViewPager中的每个片段都有自己的PDFView和DrawingView),似乎没有任何变化。

这是PdfAssetFragment继承的抽象类(这是在这里,所以我可以轻松地扩展类以允许将不同的媒体类型放在ViewPager中):

public abstract class AnnotationFragment : Fragment
{
    protected View _view;
    protected DrawingView _drawingView;

    /// <summary>
    /// ID of the fragment layout to inflate
    /// </summary>
    protected abstract int ViewId { get; }

    /// <summary>
    /// Sets up the view after it has been inflated
    /// </summary>
    protected abstract void SetupView();

    /// <summary>
    /// Creates and instantiates the view
    /// </summary>
    /// <param name="inflater">Inflate to inflate the view</param>
    /// <param name="container">Container to inflate the view into</param>
    /// <param name="savedInstanceState">Data passed from the caller</param>
    /// <returns>Inflated view</returns>
    public override View OnCreateView(
        LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
    {
        base.OnCreateView(inflater, container, savedInstanceState);
        _view = inflater.Inflate(ViewId, container, false);
        _drawingView = _view.FindViewById<DrawingView>(Resource.Id.drawing_view);

        SetupView();

        return _view;
    }

    /// <summary>
    /// Changes the type of annotation that will be drawn on the drawing view
    /// </summary>
    /// <param name="mode">New annotation mode</param>
    public void OnAnnotationTypeChanged(DrawingView.Mode mode)
    {
        _drawingView.CurrentMode = mode;
        _drawingView.TouchEventsEnabled = !mode.Equals(DrawingView.Mode.None);
    }
}

以下是PdfAssetFragment的代码:

public class PdfAssetFragment : AnnotationFragment, IOnPageChangeListener
{
    /// <summary>
    /// ID of the fragment layout to inflate
    /// </summary>
    protected override int ViewId { get { return Resource.Layout.PdfAssetFragment; } }

    /// <summary>
    /// Sets up the view after it has been inflated
    /// </summary>
    protected override void SetupView()
    {
        string t = Arguments.GetString("ASSET");
        var pdfView = _view.FindViewById<PDFView>(Resource.Id.pdf_view);
        pdfView.FromFile(new Java.IO.File(t))
               .ShowMinimap(false)
               .EnableSwipe(false)
               .OnPageChange(this)
               .Load();
    }
}

AssetPagerAdapter:

/// <summary>
/// Handles the displaying of fragments in the asset view pager
/// </summary>
public class AssetPagerAdapter : FragmentPagerAdapter
{
    private List<IMedia> _assets;
    private Context _context;

    /// <summary>
    /// Instantiates this adapter with a list of assets
    /// </summary>
    /// <param name="manager">Manager of this object</param>
    /// <param name="assets">List of assets to display</param>
    public AssetPagerAdapter(Context context, FragmentManager manager, List<IMedia> assets) : base(manager)
    {
        _context = context;
        _assets = assets;
    }

    /// <summary>
    /// Gets the number items this adapter manages
    /// </summary>
    public override int Count { get { return _assets.Count; } }

    /// <summary>
    /// Gets the next fragment to display
    /// </summary>
    /// <param name="position">Current index</param>
    /// <returns>A fragment to display in the view pager</returns>
    public override Fragment GetItem(int position)
    {
        var bundle = new Bundle();
        bundle.PutString("ASSET", _assets[position].Url);
        return PdfAssetFragment.Instantiate(_context,
            Java.Lang.Class.FromType(typeof(PdfAssetFragment)).Name,
            bundle);
    }
}

PdfAssetFragment的布局:

<FrameLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    <com.joanzapata.pdfview.PDFView
        android:id="@+id/pdf_view"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>
    <ra16.views.controls.DrawingView
        android:id="@+id/drawing_view"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_margin="@dimen/asset_view_margin"
        android:layout_weight="1"/>
</FrameLayout>

以下是我处理视图分页的方法:(在MainActivity.OnCreate()中)

_pager.PageScrolled += (sender, e) =>
{
    if (_currentFragment != null)
    {
        AnnotationTypeChanged -= _currentFragment.OnAnnotationTypeChanged;
    }

    _currentFragment = SupportFragmentManager.Fragments[e.Position]
        as AnnotationFragment;
    AnnotationTypeChanged += _currentFragment.OnAnnotationTypeChanged;
};

当我提出&#34; AnnotationTypeChanged&#34; event,触发基类AnnotationFragments OnAnnotationTypeChanged方法,并设置_drawingViews CurrentMode和TouchEventsEnabled属性。

问题是,在发生这种情况并且在drawingView上发生触摸事件之后,TouchEventsEnabled始终为false(这是默认值),这告诉我它不会发生变化。它似乎是AnnotationFragment类中的变化,因为如果我在事件处理程序中设置它们之后检查它的属性值,它们看起来就像我期望的那样。这几乎就像我不再使用相同的_drawingView了......

要为所有这些添加更多信息:我已经检查并确认每个_drawingView的ID似乎都相同..

任何帮助或建议?

0 个答案:

没有答案