मैं ASP.NET MVC दृश्य में वर्तमान क्रिया कैसे वापस कर सकता हूं?


291

मैं अपने मास्टर पेज में सीएसएस क्लास सेट करना चाहता था, जो वर्तमान नियंत्रक और कार्रवाई पर निर्भर करता है। मैं वर्तमान नियंत्रक के माध्यम से प्राप्त कर सकता हूं ViewContext.Controller.GetType().Name, लेकिन मुझे वर्तमान क्रिया कैसे मिलती है (उदाहरण के लिए)Index , Showआदि) ?

जवाबों:


83

नियंत्रक और एक्शन तत्वों दोनों को निकालने के ViewContextलिए RouteDataसंग्रह का उपयोग करें और देखें । लेकिन मुझे लगता है कि कंट्रोलर / एक्शन के बजाय कुछ डेटा वैरिएबल सेट करना जो एप्लिकेशन संदर्भ (जैसे, "एडिटमोड" या "एरर") को इंगित करता है, आपके विचारों और नियंत्रकों के बीच युग्मन को कम करता है।


आप नियंत्रक में डेटा प्राप्त कर सकते हैं और डीटीओ के साथ इसे देख सकते हैं। stackoverflow.com/a/31749391/4293929
MstfAsan

5
यह स्वीकृत उत्तर नहीं होना चाहिए, इसके बजाय सबसे अधिक मतदान वाला उत्तर देखें।
हकन फिस्टक

1
@ हकमफॉस्टोक मुझे अभी भी लगता है कि मॉडल में शब्दार्थ संबंधी जानकारी जोड़ने की सलाह सभी मामलों में एक बेहतर तरीका है कि आपके विचार में मार्ग डेटा (नियंत्रक, क्रिया) पर भरोसा करने की तुलना में भले ही दूसरा उत्तर उस डेटा को प्राप्त करने के बारे में अधिक विवरण प्रदान करता हो।
tvanfosson

467

आरसी में आप एक्शन विधि नाम की तरह रूट डेटा भी निकाल सकते हैं

ViewContext.Controller.ValueProvider["action"].RawValue
ViewContext.Controller.ValueProvider["controller"].RawValue
ViewContext.Controller.ValueProvider["id"].RawValue

MVC 3 के लिए अद्यतन

ViewContext.Controller.ValueProvider.GetValue("action").RawValue
ViewContext.Controller.ValueProvider.GetValue("controller").RawValue
ViewContext.Controller.ValueProvider.GetValue("id").RawValue

MVC 4 के लिए अद्यतन

ViewContext.Controller.RouteData.Values["action"]
ViewContext.Controller.RouteData.Values["controller"]
ViewContext.Controller.RouteData.Values["id"]

MVC 4.5 के लिए अद्यतन

ViewContext.RouteData.Values["action"]
ViewContext.RouteData.Values["controller"]
ViewContext.RouteData.Values["id"]

20
मैं इस प्री-डेट्स V2 को जानता हूं, लेकिन अब यह ViewContext.Controller.ValueProvider.GetValue("action").RawValue+ भिन्नताएं हैं
क्रिस एस

7
यह सिंटैक्स V4 में काम करता है: (स्ट्रिंग) ViewContext.RouteData.Values ​​["कार्रवाई"];
kiprainey

2
यह समाधान मेरे लिए काम नहीं करता है (MVC4 + .NET फ्रेमवर्क 4.5.1)। मेरे लिए, यह Viacheslav Smityukh: ViewContext.RouteData.Values ​​["action"], ViewContext.RouteData.Values ​​["कंट्रोलर"], ViewContext.RouteData.Values ​​["id"],
टॉमस क्यूब्स

Vk.5 में @kiprainey भी: msdn.microsoft.com/en-us/library/…
प्लूटो

2
कोशिश करें: (स्ट्रिंग) HttpContext.Request.RequestContext.RouteData.Values ​​["कार्रवाई"];
मार्टिन डॉसन

60

एक दृश्य पर वर्तमान आईडी प्राप्त करने के लिए:

ViewContext.RouteData.Values["id"].ToString()

वर्तमान नियंत्रक प्राप्त करने के लिए:

ViewContext.RouteData.Values["controller"].ToString() 

1
ViewContext.RouteData.Values ​​[<key>]। ToString () एक अपवाद को फेंकता है यदि रुटडेटा में मान मौजूद नहीं है
Grizzly Peak Software

@ShaneLarson बस ViewContext.RouteData.Values.ContainsKey(<key>)पहले के साथ अशक्त या जाँच के साथ तुलना करें ।
प्लूटो

40

मुझे पता है कि यह एक पुराना सवाल है, लेकिन मैंने इसे देखा था और मुझे लगा कि आपको वैकल्पिक संस्करण में रुचि हो सकती है, जबकि यह देखने के लिए कि आपका डेटा इसे काम करने की आवश्यकता है।

मेरी राय में एक आसान तरीका ओवरराइड करना होगा OnActionExecuting विधि । आपको ActionExecutingContext पास किया जाता है जिसमें ActionDescriptor सदस्य होता है, जिसका उपयोग आप उन सूचनाओं को प्राप्त करने के लिए कर सकते हैं जो आप देख रहे हैं, जो ActionName है और आप नियंत्रक Descriptor तक भी पहुँच सकते हैं और इसमें नियंत्रक नाम शामिल है।

protected override void OnActionExecuting(ActionExecutingContext filterContext)
{
    ActionDescriptor actionDescriptor = filterContext.ActionDescriptor;
    string actionName = actionDescriptor.ActionName;
    string controllerName = actionDescriptor.ControllerDescriptor.ControllerName;
    // Now that you have the values, set them somewhere and pass them down with your ViewModel
    // This will keep your view cleaner and the controller will take care of everything that the view needs to do it's job.
}

उम्मीद है की यह मदद करेगा। यदि कुछ भी हो, तो कम से कम यह किसी और के लिए एक विकल्प दिखाएगा जो आपके प्रश्न द्वारा आता है।


अच्छी सिफारिश; कंट्रोलर / एक्शन सेंसिंग को समझदारी से लागू करने में मेरी मदद की। धन्यवाद!
६०:०४

कार्रवाई desrciptor हो रही है कि मैं क्या जरूरत है, मैं वास्तव में किसी भी अन्य समाधान नहीं मिल रहा है तो मैं बस यहाँ कर सकते हैं और फिर क्या मैं दृश्य क्षेत्र में चाहते हैं दूर।
क्रिस मैरिकिक

17

मैंने अलग-अलग उत्तर देखे और एक वर्ग सहायक के साथ आया:

using System;
using System.Web.Mvc;

namespace MyMvcApp.Helpers {
    public class LocationHelper {
        public static bool IsCurrentControllerAndAction(string controllerName, string actionName, ViewContext viewContext) {
            bool result = false;
            string normalizedControllerName = controllerName.EndsWith("Controller") ? controllerName : String.Format("{0}Controller", controllerName);

            if(viewContext == null) return false;
            if(String.IsNullOrEmpty(actionName)) return false;

            if (viewContext.Controller.GetType().Name.Equals(normalizedControllerName, StringComparison.InvariantCultureIgnoreCase) &&
                viewContext.Controller.ValueProvider.GetValue("action").AttemptedValue.Equals(actionName, StringComparison.InvariantCultureIgnoreCase)) {
                result = true;
            }

            return result;
        }
    }
}

तो व्यू (या मास्टर / लेआउट) में आप इसका उपयोग कर सकते हैं जैसे (रेजर सिंटैक्स):

            <div id="menucontainer">

                <ul id="menu">
                    <li @if(MyMvcApp.Helpers.LocationHelper.IsCurrentControllerAndAction("home", "index", ViewContext)) {
                            @:class="selected"
                        }>@Html.ActionLink("Home", "Index", "Home")</li>
                    <li @if(MyMvcApp.Helpers.LocationHelper.IsCurrentControllerAndAction("account","logon", ViewContext)) {
                            @:class="selected"
                        }>@Html.ActionLink("Logon", "Logon", "Account")</li>
                    <li @if(MyMvcApp.Helpers.LocationHelper.IsCurrentControllerAndAction("home","about", ViewContext)) {
                            @:class="selected"
                        }>@Html.ActionLink("About", "About", "Home")</li>
                </ul>

            </div>

आशा करता हूँ की ये काम करेगा।



9

MVC में आपको सभी डेटा के साथ व्यू प्रदान करना चाहिए, व्यू को अपना डेटा इकट्ठा नहीं करने देना चाहिए ताकि आप अपने नियंत्रक कार्रवाई में सीएसएस वर्ग को सेट कर सकें।

ViewData["CssClass"] = "bold";

और अपने दृश्य में अपने ViewData से इस मान को बाहर निकालें


यह मेरी पसंदीदा विधि होगी और साथ ही नियंत्रक संरचना के आधार पर विचारों को रखने के लिए, लेकिन यह अन्यथा किया जा सकता है।
tvanfosson

1
यकीन नहीं है कि मैं इसे "CssClass" का नाम दूंगा क्योंकि ऐसा प्रतीत होता है कि प्रदर्शन तर्क आपके नियंत्रक में रेंग रहा है।
tvanfosson

सहमत, मैं आमतौर पर "संदर्भ" की तरह कुछ करता हूं, इसलिए यह प्रस्तुति परत से बंधा नहीं है, और यदि आप या तो दृश्य का नाम बदलते हैं, तो नहीं टूटते हैं।
RedFilter

6

मैं इस 2 के लिए वोट:

string currentActionName = ViewContext.RouteData.GetRequiredString("action");

तथा

string currentViewName = ((WebFormView)ViewContext.View).ViewPath;

आप वर्तमान दृश्य और क्रिया के भौतिक नाम दोनों को पुनः प्राप्त कर सकते हैं जिसने इसे ट्रिगर किया है। यह मेजबान कंटेनर को निर्धारित करने के लिए आंशिक * .acmx पृष्ठों में उपयोगी हो सकता है।


2

मैं ASP.NET MVC 4 का उपयोग कर रहा हूं, और यह मेरे लिए काम कर रहा है:

ControllerContext.Controller.ValueProvider.GetValue("controller").RawValue
ControllerContext.Controller.ValueProvider.GetValue("action").RawValue

0

विस्तार डेल Ragan के जवाब , पुन: उपयोग के लिए उनका उदाहरण, एक एप्लिकेशनकंट्रोलर वर्ग बनाएं जो नियंत्रक से प्राप्त होता है, और बदले में आपके सभी अन्य नियंत्रक नियंत्रक के बजाय उस ApplicationController वर्ग से प्राप्त होते हैं।

उदाहरण:

public class MyCustomApplicationController : Controller {}

public class HomeController : MyCustomApplicationController {}

अपने नए ApplicationController पर इस हस्ताक्षर के साथ ExecutingAction नामक एक संपत्ति बनाएं:

protected ActionDescriptor ExecutingAction { get; set; }

और फिर OnActionExecuting मेथड (डेल रागन के जवाब से), केवल इस प्रॉपर्टी को ActionDescriptor असाइन करें और जब भी आपको अपने किसी भी कंट्रोलर में इसकी आवश्यकता हो, आप इसे एक्सेस कर सकते हैं।

string currentActionName = this.ExecutingAction.ActionName;

0

इस फ़ंक्शन को अपने नियंत्रक में ओवरराइड करें

protected override void HandleUnknownAction(string actionName) 
{  TempData["actionName"] = actionName;
   View("urViewName").ExecuteResult(this.ControllerContext);
}
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.