2012-03-15 16 views
0

私は再帰モデルを持っています。C#MVC構文 - テンプレートlambda(EditorFor)で再帰的にシークします

public class Mapping 
{ 
    public string Value { get; set; } 
    public List<Mapping> ChildMappings { get; set; } 
} 

私はマッピングクラスのEditorTemplateを持っています。 EditorFor(m => m.ChildMappings)を使った通常のレンダリングは問題なく動作します。

配列パラメータ(2,3)に基づいて、特定の子孫ノードを探したいと思います。 (Mapping.ChildMappings [2] .ChildMappings [3]など)。

私は私のインデクサーと私はテンプレートで行うことができないすべてのものについてのエラーを与えたラムダ、内のローカルメソッドを呼び出して試してみました。このような、私は戻って、少なくとも、ネストされたレベルのハードコーディングされた数を容易にするために、スイッチ上に落ちてきた瞬間、については

@Html.EditorFor(m => RecurseMappings(m.BodyMappings, indexes)) 

@functions{ 
    private Mapping RecurseMappings(List<Mapping> mappings, int[] indexes) 
    { 
     Mapping mapping = new Mapping(); 

     foreach (int index in indexes) 
     { 
      mapping = mappings[index]; 
      if (mapping.ChildMappings == null) { mapping.ChildMappings = new List<RequestMapping>(); } 
      mappings = mappings[index].ChildMappings; 
     } 

     return mappings[mappings.Count - 1]; 
    } 

string[] tokens = Model.ChildIndex.Split(','); 
    int[] indexes = Array.ConvertAll<string, int>(tokens, int.Parse); 

    switch (indexes.GetLength(0)) 
    { 
     case 1: 
      { 
       var last = Model.BodyMappings[indexes[0]].ChildMappings.Count - 1; 
@Html.EditorFor(m => m.BodyMappings[indexes[0]].ChildMappings[last]) 
       break; 
      } 

     case 2: 
      { 
       var last = Model.BodyMappings[indexes[0]].ChildMappings[indexes[1]].ChildMappings.Count - 1; 
@Html.EditorFor(m => m.BodyMappings[indexes[0]].ChildMappings[indexes[1]].ChildMappings[last]) 
       break; 
      } 
     case 3: 
      { 
       var last = Model.BodyMappings[indexes[0]].ChildMappings[indexes[1]].ChildMappings[indexes[2]].ChildMappings.Count - 1; 
@Html.EditorFor(m => m.BodyMappings[indexes[0]].ChildMappings[indexes[1]].ChildMappings[indexes[2]].ChildMappings[last]) 
       break; 
      } 
     case 4: 
      { 
       var last = Model.BodyMappings[indexes[0]].ChildMappings[indexes[1]].ChildMappings[indexes[2]].ChildMappings[indexes[3]].ChildMappings.Count - 1; 
@Html.EditorFor(m => m.BodyMappings[indexes[0]].ChildMappings[indexes[1]].ChildMappings[indexes[2]].ChildMappings[indexes[3]].ChildMappings[last]) 
       break; 
      } 
     case 5: 
      { 
       var last = Model.BodyMappings[indexes[0]].ChildMappings[indexes[1]].ChildMappings[indexes[2]].ChildMappings[indexes[3]].ChildMappings[indexes[4]].ChildMappings.Count - 1; 
@Html.EditorFor(m => m.BodyMappings[indexes[0]].ChildMappings[indexes[1]].ChildMappings[indexes[2]].ChildMappings[indexes[3]].ChildMappings[indexes[4]].ChildMappings[last]) 
       break; 
      } 
     default: 
      break; 
    } 

だから、何をラップする方法はあります私は失敗した最初の試みのようなパッケージで働いていますか?ラムダコードブロックを試しましたが、式ツリーに変換できないため拒否されました。ソースで

@{ 
    var dd = new ViewDataDictionary<Mapping>(RecurseMappings(Model.BodyMappings, indexes)); 
    var dc = new MyDataContainer() { ViewData = dd }; 
    var help = new HtmlHelper<Mapping>(ViewContext, dc); 
} 

@help.EditorFor(m => m) 

カスタムデータの定義ファイル:

答えて

1

まあ、おそらくこれが意図した方法ではありませんが、あなたは、あなたが手にするオブジェクトのための新しいHTMLヘルパーを作成するとき、それは動作しますコンテナは、インターフェイスを実装するクラスを見つけることができませんでした。

public class MyDataContainer : IViewDataContainer 
{ 
    public ViewDataDictionary ViewData { get; set; } 
} 
+0

これは私に同じランタイムエラーを与えています(デバッグすると、メソッドを入力しようとしないことを示します)。 ユーザーコードによってSystem.InvalidOperationExceptionが処理されませんでした。 メッセージ=テンプレートは、フィールドアクセス、プロパティアクセス、1次元配列インデックス、または単一パラメータカスタムインデクサ式でのみ使用できます。 – Wraith404

+0

これは壊れていないが、複数の要素(すべてが階層構造になっている)とやや不適切なモデルバインディングを提供しているので、これはより近づいています。結果は、名前で最上位の親にバインドする必要があります。または、親モデルの "BodyMappings"コレクションコンポーネントとして投稿することはできません。 – Wraith404

関連する問題