วิธีใช้ RX จะควบคุมคำสั่งเป็นตั้งค่าโครงการในซับซ้อนเหตุการณ์จำลอง?

0

คำถาม

ที่ตั้งค่า

ลองสันนิษฐานว่าเออออตามหรอกนะ เรามีคนติดตาม ทฤษฎีนั้น viewmodel ชั้นเรียนสำหรับ WPF องโปรแกรม:

public MyViewModel
{

    public MyViewModel()
    {
        // Condition under which this command may be executed is:
        // this.ActiveDocument.Highlighting.Type == Highlighting.Xml && 
        //    !this.ActiveDocument.IsReadOnly && 
        //    (this.License.Kind == LicenseKind.Full || this.License.TrialDay < 30)
        MyCommand = new Command(obj => DoSomething());
    }

    public ICommand MyCommand { get; } 
    // (all other required properties)
}

ที่เพิ่มมานอกเหนือจาก:

  • ปัจจุบันเรียน implements เหมาะสม INotifyPropertyChanged
  • คลาสทั้งหมดในสมาชิกเข้าใช้งานล่ามโซ่ implements เหมาะสม INotifyPropertyChanged (eg. เอกสาร viewmodel สามารถเข้าใช้จาก ActiveDocument ทรัพย์สิน)
  • ActiveDocument อาจจะเป็น null. ActiveDocument.Highlighting อาจจะเป็นโพรโทคอล aimcomment.

มีปัญหา

ฉันอยากคำสั่งที่จะถูกเปิดใช้งานเดียวตอนนี้อาการป่วยในความเห็นคือพบกัน

ตัวเลือกโดยไม่มี RX

ฉันเขียน ของตัวเองสมุด สำหรับการจัดการสถานการณ์เช่นนี้. ทางออกที่จะเป็นเหมือนกั:

public MyViewModel
{
    private readonly Condition commandAvailableCondition;

    public MyViewModel()
    {
        commandAvailableCondition = new LambdaCondition(this, 
            vm => m.ActiveDocument.Highlighting.Type == Highlighting.Xml && 
                !vm.ActiveDocument.IsReadOnly && 
                (vm.License.Kind == LicenseKind.Full || vm.License.TrialDay < 30),
            false);

        MyCommand = new AppCommand(obj => DoSomething(), commandAvailableCondition);
    }

    public ICommand MyCommand { get; } 
    // (all other required properties)
}

หรือถ้าคุณต้องการรหัสเป็นมากกว่านี้หน่อสามารถอ่านได้ดังนั้นบางส่วนเงื่อนไขอาจเป็น reused-เหมือนว่า:

public MyViewModel
{
    private readonly Condition commandAvailableCondition;

    public MyViewModel()
    {
        var highlightingIsXml = new LambdaCondition(this, 
            vm => vm.ActiveDocument.Highlighting.Type == Highlighting.Xml, 
            false);
        var documentIsReadonly = new LambdaCondition(this,
            vm => vm.ActiveDocument.IsReadOnly, 
            false);
        var appIsLicensed = new LambdaCondition(this,
            vm => vm.License.Kind == LicenseKind.Full || this.License.TrialDay < 30,
            false);

        commandAvailableCondition = highlightingIsXml & !documentIsReadonly & appIsLicensed;

        MyCommand = new AppCommand(obj => DoSomething(), commandAvailableCondition);
    }

    public ICommand MyCommand { get; } 
    // (all other required properties)
}

อะไรของฉันห้องสมุด(หรือมากกว่าถูกต้อง, LambdaCondition ชั้นเรียน)มันคือ:

  • มันทำให้ตามรของโห implementing INotifyPropertyChanged และจัดการเปลี่ยนแปลง(eg. ตอนที่ ActiveDocument เปลี่ยนแปลงหรือ ActiveDocument.Highlighting เปลี่ยนแปลงหรือ ActiveDocument.Highlighting.Type เปลี่ยนแปลงเป็นต้น)
  • มันทำให้ตามความเป็นไปได้ว่าเขาจะเป็น nullเออยู่บนทางในกรณีนั้นมันจะต้องกลับมาค่าปริยาย(ในกรณีนี้ false)
  • มันจะโดยอัตโนมัติรายงานเปลี่ยนแปลง(แต่เดียวที่เปลี่ยนแปลง)ของตั้งค่าโครงการจะบังคับบัญชา"ดังนั้นส่วนติดต่อผู้ใช้ขออาจจะปรับปรุงข้อมูลแล้วตอนที่ต้องการ

คำถาม

ว่าเป็นเพียงคนเดียด้วยอะไรซักอย่างที่สร้างสถานการณ์จำลอเรียกเหนือการใช้ System.Reactive ใน C#? มันเป็นไปได้ที่จะทำมันอย่างง่ายดายขณะที่ชอบเก็บทุกอย่างเรื่องความต้องการ INotifyPropertyChanged,nulls ระหว่างทางและค่าปริยาย? คุณอาจจะทำให้มีสติดีทุกตั้งสมมติฐานตอนที่ต้องการ

c# mvvm system.reactive wpf
2021-11-23 15:15:48
1

คำตอบที่ดีที่สุด

0

ที่ ReactiveUI เฟรมเวิร์กมี ReactiveCommand ชั้นเรียนนั่นใช้การ IObservable<T> ต้องการเรียกปรับปรุงสถานะของคำสั่ง(i.e. เลี้ยง CanExecuteChanged เหตุการณ์ของคน ICommand).

ได้โปรดอ้างอิง docs สำหรับเป็นตัวอย่างของวิธีใช้มันเพื่อควบคุม executability:

var canExecute = this.WhenAnyValue(
    x => x.UserName, x => x.Password,
    (userName, password) => 
        !string.IsNullOrEmpty(userName) && 
        !string.IsNullOrEmpty(password));

var command = ReactiveCommand.CreateFromTask(LogOnAsync, canExecute);
2021-11-24 14:52:33

มันตาม INotifyPropertyChange implementers อยู่ในพื้นที่ใช้งานลูกโซ่? มันยังทำงานเหมาะสมถ้ามีคุณสมบัติคือโพรโทคอล aimcomment? คุณช่วยแสดงวิธีของฉันระบุตัวอย่างเช่นคงดูตอนที่ติดตั้งเพื่อใช้งานใน RX?
Spook

WhenAnyValue มันส่งเสีค่าใหม่ตอนที่ไหน Username แล้ว Password คุณสมบัติของ rasises ง PropertyChanged เหตุการณ์. มันคืออะไรของคุณระบุตัวอย่างเช่นกันแน่? สิ่งที่คุณลองไหม?
mm8

เธออ่านของฉันทั้งคำถามเหรอ? ฉันเสนอส่วนผสมที่แน่นอนเงื่อนไขซึ่งควรจะมองดู: vm => m.ActiveDocument.Highlighting.Type == Highlighting.Xml && !vm.ActiveDocument.IsReadOnly && (vm.License.Kind == LicenseKind.Full || vm.License.TrialDay < 30), แล้วถ้า eg. ActiveDocument คือโพรโทคอล aimcomment? จะ RX รับมือกับมันเหมาะสม? ฉันคาดหวังในกรณีนี้สภาต้องของมันค่าปริยาย(หรืออย่างน้อยปลอมโดยปริยาย)
Spook

ถ้า ActiveDocumentคุณจะได้ NullReferenceException. นี่มันไม่เกี่ยวกับ RX.
mm8

อยู่ในห้องสมุดฉันจะไม่. นั่นมันอยู่ในหมู่คนอื่นเป็นเหตุผลว่าทำไมฉันสนใจว่า RX คือเหมาะสำหรับงานนี้.
Spook

ในภาษาอื่นๆ

หน้านี้อยู่ในภาษาอื่นๆ

Русский
..................................................................................................................
Italiano
..................................................................................................................
Polski
..................................................................................................................
Română
..................................................................................................................
한국어
..................................................................................................................
हिन्दी
..................................................................................................................
Français
..................................................................................................................
Türk
..................................................................................................................
Česk
..................................................................................................................
Português
..................................................................................................................
中文
..................................................................................................................
Español
..................................................................................................................
Slovenský
..................................................................................................................

ดังอยู่ในนี้หมวดหมู่

ดังคำถามอยู่ในนี้หมวดหมู่