Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to update binding after validation #584

Closed
awaynemd opened this issue Nov 7, 2023 · 4 comments
Closed

How to update binding after validation #584

awaynemd opened this issue Nov 7, 2023 · 4 comments

Comments

@awaynemd
Copy link

awaynemd commented Nov 7, 2023

High-level description
Describe your issue.

Steps to Reproduce
Strongly consider linking to a GitHub repository containing an application that reproduces your problem. Ideally you have tired to obtain a minimal working example. All four of the items in the External Links section in that Wikipedia article are excellent.

Steps to reproduce the behavior:

  1. Go to '...'
  2. Click on '....'
  3. Scroll down to '....'
  4. See error

Expected or desired behavior
Describe what you expected or wanted to happen.

Actual behavior
Describe what actually happens. Consider including a screen recording of the actual behavior via a GIF. ShareX is one program that can capture a screen recroding and save it to a GIF.

Additional Information
Elmish.WPF version: ???
Target framework version: ???

Add any other context about the problem here.

@awaynemd
Copy link
Author

awaynemd commented Nov 7, 2023

In Elmish.WPF I am using the following code:

"Copay" |> Binding.twoWayOpt((fun m ->Some (Copay.value m.Copay)), SetCopay)
> Binding.addValidation(fun m -> match m with
|{Copay = Copay.InvalidCopay d} -> ["Invalid Copay"]
| _ -> []

Where "Copay" is the bound property to WPF and the model defines Copay as:
Copay: Copay.T

module Copay =
type CopayData = { copay: string}
type T =
| ValidCopay of CopayData
| InvalidCopay of CopayData

    let formatMaskTextBox (s:string) = Regex.Replace( s, @"[^0-9.]","")

    let (|IsCopay|_|) (s:string) = if Regex.IsMatch(s,@"^\d{1,3}.\d{1,2}$") then Some (IsCopay s) else None

    // Define the constructor
    let create (ss: string option) = 
        match ss with
        |None -> InvalidCopay {copay = ""}
        |Some s -> match formatMaskTextBox s with
                   | IsCopay  t -> t |> float |> (fun d -> ValidCopay {copay = sprintf"%3.2f" d})  
                   | _ -> InvalidCopay {copay = s}
        

    // Define deconstructors/ unwrap.  Using "dot" notation to decompose the record.
    let value (f:T) = match f with
                      | ValidCopay d -> d.copay
                      | InvalidCopay d -> d.copay  

    let valueOption (f:T) = match f with
                            | ValidCopay d -> Some d.copay
                            | InvalidCopay d -> None

and SetCopay is:
|SetCopay p -> {m with Copay = Copay.create p}, Cmd.ofMsg InvalidatePolicy

All works correctly to validate an input digital payment. However, the "get" of the binding is executed only once before the
validation code reformats the copay. Hence, the wpf display does not show the "reformatted" input.

Is there anyway to force the binding to update AFTER the validation code is run?

Thanks

@marner2
Copy link
Collaborator

marner2 commented Nov 7, 2023

Can you format your question better? I'm not seeing your validation code.

To try to answer the question generally, though, remember that Elmish.WPF utilizes an MVU architecture. The View only updates after an Update is applied to the Model. So any updates to the Model that aren't through an Update message will not be seen by the View until some other Update happens (the binding in this case is the View).

@awaynemd
Copy link
Author

awaynemd commented Nov 7, 2023

@marner2 Thank you for your response. I don't see how to reformat the above without copy/paste ? The validation code is being performed with the "match" statement just below the "Copay" binding.

As to your answer, I'm hopeful there is an override (of some sort) that would allow the ".addValidtion" to trigger an update???

@marner2
Copy link
Collaborator

marner2 commented Nov 8, 2023

Binding.addValidation doesn't actually modify the underlying binding. It sets a parallel error object that WPF error templates can read and display (think of it like an extra bit of information attached to the "CoPay" binding). See Data Validation -> Providing Visual Feedback in the WPF docs about Bindings for more information on how that works.

If you're wanting to modify the actual value in the model so that the "CoPay" binding updates, you would need to do that by modifying the model inside the Update function.

@awaynemd awaynemd closed this as completed Nov 8, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants