Pergunta

Esperançosamente, isso deve ser simples.

Gostaria de adicionar um método de extensão à classe System.Web.Mvc.ViewPage< T >.

Como deve ser esse método de extensão?

Meu primeiro pensamento intuitivo é mais ou menos assim:

namespace System.Web.Mvc
{
    public static class ViewPageExtensions
    {
        public static string GetDefaultPageTitle(this ViewPage<Type> v)
        {
            return "";
        }
    }
}

Solução

A solução geral é esta resposta.

A solução específica para estender a classe System.Web.Mvc.ViewPage é minha resposta abaixo, que começou a partir do solução geral.

A diferença está no caso específico de que você precisa de uma declaração de método de tipo genérico E de uma instrução para impor o tipo genérico como um tipo de referência.

Foi útil?

Solução

Não tenho o VS instalado na minha máquina atual, mas acho que a sintaxe seria:

namespace System.Web.Mvc
{
    public static class ViewPageExtensions
    {
        public static string GetDefaultPageTitle<T>(this ViewPage<T> v)
        {
            return "";
        }
    }
}

Outras dicas

Obrigado, Leddt.Fazer isso gerou o erro:

O tipo 'tmodel' deve ser um tipo de referência para usá -lo como parâmetro 'tmodel' no tipo ou método genérico

que me indicou esta página, que rendeu esta solução:

namespace System.Web.Mvc
{
    public static class ViewPageExtensions
    {
        public static string GetDefaultPageTitle<T>(this ViewPage<T> v) 
          where T : class
        {
            return "";
        }
    }
}

Ele só precisa do especificador de tipo genérico na função:

namespace System.Web.Mvc
{
    public static class ViewPageExtensions
    {
        public static string GetDefaultPageTitle<Type>(this ViewPage<Type> v)
        {
            return "";
        }
    }
}

Editar:Só perdi por segundos!

namespace System.Web.Mvc
{
    public static class ViewPageExtensions
    {
        public static string GetDefaultPageTitle<T>(this ViewPage<T> view)
            where T : class
        {
            return "";
        }
    }
}

Você também pode precisar/desejar adicionar o qualificador "new()" ao tipo genérico (ou seja,"onde T:class, new()" para garantir que T é um tipo de referência (classe) e possui um construtor sem parâmetros.

Glenn Block tem um bom exemplo de implementação de um ForEach método de extensão para IEnumerable<T>.

Dele postagem no blog:

public static class IEnumerableUtils
{
    public static void ForEach<T>(this IEnumerable<T> collection, Action<T> action)
    {
        foreach(T item in collection)
            action(item);
    }
}

Se você deseja que a extensão esteja disponível apenas para o tipo especificado, você simplesmente precisa especificar o tipo real que você estará lidando

algo como...

public static string GetDefaultPageTitle(this ViewPage<YourSpecificType> v)
{
  ...
}

Observe que o intellisense exibirá apenas o método de extensão quando você declarar sua (neste caso) ViewPage com o tipo correspondente.

Além disso, é melhor não usar o namespace System.Web.Mvc, sei que é conveniente não precisar incluir seu namespace na seção de usos, mas é muito mais fácil de manter se você criar seu próprio namespace de extensões para suas funções de extensão.

Aqui está um exemplo para visualizações do Razor:

public static class WebViewPageExtensions
{
    public static string GetFormActionUrl(this WebViewPage view)
    {
        return string.Format("/{0}/{1}/{2}", view.GetController(), view.GetAction(), view.GetId());
    }

    public static string GetController(this WebViewPage view)
    {
        return Get(view, "controller");
    }

    public static string GetAction(this WebViewPage view)
    {
        return Get(view, "action");
    }

    public static string GetId(this WebViewPage view)
    {
        return Get(view, "id");
    }

    private static string Get(WebViewPage view, string key)
    {
        return view.ViewContext.Controller.ValueProvider.GetValue(key).RawValue.ToString();
    }
}

Você realmente não precisa usar a versão genérica, pois a genérica estende a não genérica, então basta colocá-la na classe base não genérica e pronto :)

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top