1

I have a view model in Xamarin Forms using Prism framework. I have a lot of UI elements that have, each, lots of bind properties in my view model that have similar behaviour. After a command action, I want to perform exactly the same logic for each of these elements without having to duplicate the same logic all over for each.

To be more concrete. I have landmarks over a picture. Each landmark can be dragged. Each landmark has a command to activate the dragging mode, which changes the icon of the landmark and the size of it. When I create a method to modularise this behaviour in a single method, receiving as a parameter, each of the landmark bind properties, the setter of the properties is never triggered, thus the UI element is never changed.

This is what I've tried:

My landmark XAML

<Controls:LandmarkView 
    DragMode="Touch" 
    LBounds="{Binding ChinLandmarkBounds, Mode=TwoWay}" 
    DragDirection="All"
    IsVisible="{ Binding AreLandmarksVisible }"
    ToggleDraggingCommand="{Binding ChinToggleDraggingCommand}"
    DraggingBoundaries="{Binding ChinDraggingBoundaries}">
    <Controls:LandmarkView.Content>
        <AbsoluteLayout>
            <Image BackgroundColor="#72C8BB" 
                 WidthRequest="{Binding LandmarkLineWidth}" 
                 AbsoluteLayout.LayoutBounds= "{Binding LandmarkLineXPos}"
                 AbsoluteLayout.LayoutFlags= "YProportional,WidthProportional"/>
            <ffimageloading:CachedImage 
                WidthRequest="{Binding ChinSize}"
                HeightRequest="{Binding ChinSize}"
                Source="{Binding ChinLandmarkIcon, Converter={StaticResource SvgImageSourceConverter}}">
            </ffimageloading:CachedImage>
        </AbsoluteLayout>
    </Controls:LandmarkView.Content>
</Controls:LandmarkView>

The command in the view model for the dragging toggling:

public ICommand ChinToggleDraggingCommand { get; set; }

The landmark bind properties:

private Rectangle _chinLandmarkBounds;
    public Rectangle ChinLandmarkBounds
    {
        get { return _chinLandmarkBounds; }
        set
        {
            SetProperty(ref _chinLandmarkBounds, value);
            CalculateMouthRightEdgeDraggingBoundaries();
            CalculateMouthLeftEdgeDraggingBoundaries();
            CalculateChinDraggingBoundaries();
        }
    }
    private string _chinLandmarkIcon;
    public string ChinLandmarkIcon
    {
        get { return _chinLandmarkIcon; }
        set { SetProperty(ref _chinLandmarkIcon, value); }
    }
    private Rectangle _chinDraggingBoundaries;
    public Rectangle ChinDraggingBoundaries
    {
        get { return _chinDraggingBoundaries; }
        set { SetProperty(ref _chinDraggingBoundaries, value); }
    }
    private int _chinSize;
    public int ChinSize
    {
        get { return _chinSize; }
        set { SetProperty(ref _chinSize, value); }
    }

The method I would like to call for each landmark that doesn't trigger the property setter:

private void ToggleDraggingMode(Rectangle landmarkBounds, string landmarkIcon, int size, bool activateDraggingMode)
    {
        if (activateDraggingMode)
        {
            landmarkIcon = ControlsArrowsAllRed;
            size = size * 2;
            landmarkBounds = new Rectangle((double)landmarkBounds.X - size / 2, (double)landmarkBounds.Y - size / 2, size, size);
        }
        else
        {
            landmarkIcon = ControlsRedFull;
            size = size / 2;
            landmarkBounds = new Rectangle(landmarkBounds.X + size / 2, (double)landmarkBounds.Y + size / 2, size, size);
        }
    }

The call to the previous method:

ToggleDraggingMode(ChinLandmarkBounds, ChinLandmarkIcon, ChinSize, activateDraggingMode);

How can I pass my bind properties as parameters of a method and make the setter be called when I assign a value to the method parameter (in the previous code, the landmarkBounds local variable)?

Thanks

marcp
  • 1,179
  • 2
  • 15
  • 36
jcasas
  • 305
  • 4
  • 12

0 Answers0