ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace...

34
ÚLTIMA ACTUALIZACIÓN: 17 DE OCTUBRE DE 2013 Servicio de Informática | Universidad de Alicante ASP.NET MVC 4 ELEMENTOS GRÁFICOS Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es/

Transcript of ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace...

Page 1: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ÚLTIMA ACTUALIZACIÓN: 17 DE OCTUBRE DE 2013

Servicio de Informática | Universidad de Alicante

ASP.NET MVC 4

ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante

Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es/

Page 2: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

2

GUÍA DE ESTILO

Con el objetivo de conseguir un diseño de aplicaciones común, se ha preparado una guía de estilo con

los elementos básicos para el desarrollo de aplicaciones.

Actualmente sólo está disponible en nuestras máquinas de desarrollo y lo podemos encontrar en

nuestra carpeta compartida del aula.

El ejemplo de un listado con su gestión lo podemos ver en la imagen siguiente

La guía dispone de documentación de los elementos gráficos más comunes; avisos, botones,

calendarios, listados, etc. Con el desarrollo de nuevas aplicaciones en este entorno se irán

incorporando nuevas funcionalidades o elementos.

SEGUIDAD

Se han incorporado ejemplos de identificación con LDAP y en breve como integrarlo con el Sistema de

Identifiación Único (CAS). Se apoya en las librerías desarrolladas en el Servicio de Informática.

No sólo permite identificarse sino que permite personalizar a dónde puede acceder ese usuario o el

rol al que pertenece.

Igualmente se ha implementado un sistema para obligar a la identificación en entornos SSL. Hasta el

momento se dejaba al programador esta tarea, que en muchas ocasiones se nos olvidaba o no le

dábamos poca importancia. Ahora está completamente integrado con lo que su uso se hace obligatorio

a la hora de identificarse.

Page 3: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

3

DISEÑO SENSIBLE

Cada vez es más frecuente encontrar Webs que se adaptan al dispositivo que se conectan sin tener

que crear plantillas diferentes para cada uno, a eso se le llama diseño sensible (responsive design).

Nuestra plantilla se ve correctamente en un navegador de escritorio

Como en un móvil

Cada vez es más frecuente el acceso a nuestra web desde dispositivos móviles o tabletas. Permitir el

acceso y uso de nuestras aplicaciones desde estos dispositivos las hacen más atractivas.

Page 4: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

4

RAZOR EN DETALLE

MODELO

En la mayoría de los casos la vista trabaja con los datos de un modelo.

Por eso nos podemos encontrar con dos casos, que le enviemos un único registro (por ejemplo para

operaciones de creación o edición) o con un conjunto de datos (por ejemplo listados).

Modelo con un único registro

Por ejemplo para ver los detalles de un libro. Incluiremos @model RutaModelo al principio de la vista.

@model MvcAnuncio3.Models.CSI_CATEGORIA

Luego para usarlo dentro del código haremos referencia directamente al objeto model

@Html.EditorFor(model => model.NOMBRE_ES)

Modelo con un conjunto de datos

Por ejemplo para ver el listado de libros. Incluiremos @model IEnumerable <RutaModelo> al principio

de la vista.

@model IEnumerable<MvcAnuncio3.Models.CSI_CATEGORIA>

Luego para usarlo, por ejemplo en un bucle

@foreach (var item in Model) { .. @Html.DisplayFor(modelItem => item.NOMBRE_ES) .. }

Layout

Es el equivalente a las MasterPages en WebPages, es decir la plantilla común para todas las páginas de

nuestro sitio.

Por defecto al crear un proyecto MVC nos crea en la carpeta Views > Shared el fichero _Layout.cshtml.

Esta página es la plantilla que usará el asistente de las vistas cuando no seleccionamos ninguna.

Se puede seleccionar cualquier otra en el momento que creamos la vista

Page 5: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

5

o accediendo al código de la vista generado y añadido la línea Layout = “Fichero con la plantilla para

la vista”

@{ Layout = "~/Views/Shared/_Layout.cshtml"; }

@RenderBody()

Se utiliza en _layout.cshtml para indicar que en ese punto se incluirá el código generado por la vista.

Todos los layouts deben incluirla. En caso de no hacerlo obtendremos el siguiente mensaje de error.

Error de servidor en la aplicación '/'.

No se ha llamado al método "RenderBody" para la página de diseño "~/Views/Shared/_layout.cshtml".

Page 6: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

6

@section

Definimos una sección de código Razor / HTML que se insertará en el layout en caso de que se llame a

@rendersection con el nombre de la sección que hayamos declarado.

@section NombreSección { …

}

Si queremos definir una sección cabecera, en cada vista la definiríamos del siguiente modo. @section cabecera { <h1>Ejemplo de sección</h1> }

@RenderSection

Incluimos en nuestra plantilla secciones o bloques de código Razor / HTML que se ha definido en la

vista. Podemos indicar además si es obligatorio o no definirla.

@RenderSection("NombreSección ", required: false / true)

Por defecto toma el valor true, con lo que en caso de que no la incluyamos en nuestra vista, dará un

mensaje de error.

Sección no definida: "cabecera".

Descripción: Excepción no controlada al ejecutar la solicitud Web actual. Revise el seguimiento de la pila para obtener más

información acerca del error y dónde se originó en el código.

@RenderSection("cabecera", required:false)

IsSectionDefined

Por último para controlar si se ha definido la sección, disponemos de la función IsSectionDefined().

Siguiendo con el ejemplo de la cabecera podríamos comprobar si se ha definido para darle un formato

y sino le damos otro formato.

@if (IsSectionDefined("cabecera")) { <div id="title"> @RenderSection("cabecera") </div> } else { <div id="titledefalt"><h1 class="generico">Título genérico</h1></div> }

Etiquetas avanzadas

@()

En caso de que una variable, dentro del código, pueda provocar confusión, podemos usar @(variable).

Por ejemplo

Page 7: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

7

<img src="images/"@model.foto.jpg" />

No podríamos afimar si está llamando a @model.foto y luego incorpora la extensión .jpg o que

interprete que .jpg es una propiedad de @model.foto.

Deberíamos utilizar

<img src="images/"@(model.foto).jpg" />

Para evitar este conflicto.

@:

Aunque ya lo vimos ayer, lo vuelvo a remarcar. Aquel texto HTML que no incluya etiquetas puede

provocar que se interprete como código Razor.

<span> @if(true){ La hora es: @DateTime.Now } else { Aquí no se debería acceder nunca } </span>

No sabe si es código HTML o código C#. Para definírselo anteponemos @: (si sólo es una línea) para

decirle que es HTML

<span> @if(true){ @:La hora es: @DateTime.Now } else { @:Aquí no se debería acceder nunca } </span>

Es equivalente a incluir el texto entre las etiquetas <text></text>

Html.Raw

Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3).

Puede que en ocasiones necesitemos que sea así (por ejemplo porque incluye etiquetas de formato),

aunque debemos tener mucho cuidado con el contendido para que no nos produzcan XSS Injection.

<h2>@Html.Raw(ViewBag.Message)</h2>

Page 8: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

8

Partial Views

Como conocemos las vistas hasta ahora genera una página web en cada llamada. Con un layout por

defecto o personalizado, pasando por el código generado por la vista y terminando con secciones

opcionales o no.

Esto no lo hace muy complicado de mantener y sobre todo poco flexible. Por eso existen las vistas

parciales que permiten dividir la página en bloques más pequeños lo que las hace más fácil de

gestionar.

Puede ser muy útil en llamada AJAX porque el código generado es el que le indiquemos en la vista

parcial sin elementos como layout que se supone que se ha llamada anteriormente desde una vista.

Con un ejemplo lo vamos a ver muy claro.

Queremos hacer la suma de dos números es un método del controlador Home. Pasamos dos

parámetros y cambiamos return View(); por return PartialView();

public ActionResult Suma(int numero1, int numero2) { ViewBag.Suma = numero1 + numero2; return PartialView(); }

Ahora creamos la vista y la marcamos como parcial

Escribimos el resultado en la vista vacía (que no tiene ni model, ni layout)

@ViewBag.Suma

¿Cómo la llamamos? Lo normal es hacerlo como hasta ahora

http://servidor/home/suma?numero1=5&numero2=7

Page 9: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

9

pero como es lógico el propósito no era éste. Nosotros queremos incluirlo dentro de otra vista y lo

vamos a hacer con AJAX, es decir se cargará una vista inicial y ante un evento modificaremos el

contenido de algún elemento de la vista inicial con el contenido de la vista parcial.

Incluimos el siguiente código en algún método de home

La suma de 5 y 7 es: <span id="operacion"></span> <script type="text/javascript"> $(function(){ $("#operacion").load("/home/Suma?numero1=5&numero2=7"); }); </script>

La primera línea pone un texto y prepara una etiqueta donde luego mostrar el resultado.

Las siguientes líneas son javascript y JQuery. Esta librería está muy integrada en Visual Studio con lo

que debemos aprovechar que la disponemos. Lo que hace es llamar a nuestro controlador con load y

poner el resultado en aquella etiqueta que tenga como id operacion ($(“#idetiqueta”)).

Visualmente vemos el resultado de la operación, pero internamente ha hecho una segunda llamada

para obtener el resultado de la suma y luego ha modificado el contenido de la etiqueta.

No es obligatorio llamarlo desde javascript y con AJAX, podemos llamarlo desde nuestras propias

vistas. El ejemplo de ayer que mostrábamos un listado de alumnos. Usamos el siguiente código

<p>Listado de alumnos</p> <ul> @foreach (var item in Model) { <li>@item.Nombre @item.Apellidos</li> } </ul>

Si el formato de la ficha del alumno fuera muy amplia, sería una buena solución convertirla en una

vista parcial y llamarla desde nuestra propia vista

<p>Listado de libros (Vistas parciales)</p> @foreach (var item in Model) { @RenderPage("~/Views/Home/Formato.cshtml", new {alumno = item}); }

Para recoger los parámetros tenemos que usar el objeto Page y como propiedad lo que hayamos

pasado, en este caso libro y trabaríamos con las propiedades de éste como si fuera el modelo.

@{ var Model = Page.alumno; } <div> <strong>Nombre: </strong> @Model.Nombre </div> <div style="margin-bottom: 20px;"> <strong>Apellidos: </strong> @Model.Apellidos </div>

Page 10: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

10

En este segundo caso no se hace una llamada por cada libro, ya que se hace internamente antes de

devolver la página completa.

HELPERS

Los Helpers podríamos entenderlo como una forma de facilitar de reutilizar código que escribimos en

muchas ocasiones.

MVC nos ofrece de dos tipos:

HTMLHelpers orientados a escribir código HTML. La mayoría de métodos que nos ofrece son

para trabajar con formularios, simplificando y unificando enormemente este proceso.

URLHelpers orientada a simplificar el trabajo con direcciones y conversiones de caracteres.

En el día de hoy nos centraremos en los segundos porque son muy pocos y los necesitamos para poder

crear nuestro primer layout / plantilla.

URLHelper

Para poder usar este Helper dentro del motor Razor antepondremos @Url al método que queramos

llamar. Por ejemplo si queremos poner la ruta de nuestro fichero css, en el layout por defecto hace

uso del método Content de URLHelper.

<link href="@Url.Content("~/Content/Site.css")" rel="stylesheet" type="text/css" />

La integración es muy sencilla porque no debemos hacer ninguna referencia externa y dispone de

intellisense lo que facilita su escritura.

Los 4 métodos que lo forman son

Action(s:action, s:controller, …)

Genera la dirección completa de la llamada a un método / acción de un controlador.

Por ejemplo si queremos crear un enlace a Acerca de, podríamos usar el siguiente código HTML

<a href="@Url.Action("About", "Home")">Acerca de</a>

Si queremos hacer una llamada a un método Buscar al que le pasemos el término de búsqueda,

incluiríamos un tercer campo, con los parámetros que queramos personalizar.

<a href="@Url.Action("Buscar", "Home", new { busqueda = "Servicio de Informática" })">Buscar por "Servicio de Informática"</a>

Si el método permite la recepción del parámetro “busqueda”, entonces lo podríamos usar.

public ActionResult Buscar(string busqueda) { ViewBag.Search = busqueda; return View(); }

Page 11: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

11

Content(s:path)

Convierte una dirección virtual / relativa en su correspondiente dirección absoluta de la aplicación. Es

muy útil cuando hacemos referencia a ficheros como hojas de estilo o javascript

<link href="@Url.Content("~/Content/Site.css")" rel="stylesheet" type="text/css" />

Encode(s:url)

Codifica los caracteres especiales de una URL por sus equivalentes caracteres estándar.

Se usa para evitar problemas con ciertos navegadores que no interpretan los caracteres especiales.

En el ejemplo anterior el envío de “Servicio de Informática” sería uno de los casos que nos podrían dar

errores por os espacios y acento.

<a href="@Url.Action("Buscar", "Home", new { busqueda = Url.Encode("Servicio de Informática") })">Buscar por "Servicio de Informática"</a>

La dirección que nos genera es

http://servidor/Home/Buscar?busqueda=Servicio%2Bde%2BInform%25c3%25a1tica

RouteUrl(s:route)

Muy parecido al primero pero todo en uno, es decir pasamos los parámetros que queramos en un

único parámetro, de la siguiente manera new { Controller = “…”, Action = “…”, …}

La misma llamada Acerca de pero con RouteUrl sería.

<a href="@Url.RouteUrl(new {Controller = "Home", Action = "About"})">Acerca de</a>

Si queremos pasar también el campo de búsqueda (o el id)

<a href="@Url.RouteUrl(new {Controller = "Home", Action = "Buscar", busqueda = "Servicio de Informática" })">Buscar por "Servicio de Informática"</a>

Mañana nos centraremos en los HTMLHelpers y veremos como crear los nuestros propios.

HTMLHelpers

Ayer vimos las funciones relacionadas con las direcciones. Hoy nos centramos en las que realmente

nos van a ayudar en el trabajo diario, las que nos generan código HTML.

Aunque el listado es mucho más amplio que el de URLHelpers, lo cierto es que todos son muy

parecidos.

Page 12: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

12

Vamos a comenzar con el elemento básico que es el formulario que recoge todos los campos con los

que trabajamos.

Nos creamos una método / acción en nuestro controlador para ir jugando. Le podemos llamar helpers.

No le vamos a pasar ningún modelo por el momento.

Editamos su vista y lo básico para un formulario en HTML es <form …></form>.

La idea es que no lo escribamos directamente sino que usemos los helpers.

BeginForm(s:action, s:controller, o:values)

Si escribimos

@using (Html.BeginForm()) { }

Nos generaría el siguiente código

<form action="/Home/helpers" method="post"></form>

Por defecto nos genera una acción a nosotros mismos y hace la llamada con método post

Con los parámetros podemos indicar que controlador / acción del action y el método

Html.BeginForm("Create", "Alumno", FormMethod.Get)

Y generaría

<form action="/Alumno/Create" method="get"></form>

Todos los HTMLHelpers incluyen un último parámetro abierto a añadir cualquier atributo HTML, por

ejemplo id, class, etc. En el caso de que queramos indicar el id

Html.BeginForm("Create", "Alumno", FormMethod.Get, new {id="fTest"}))

Si además quisiéramos añadir el estilo con class al ser una palabra reservadas del sistema debemos

escribir la propiedad con @class.

Html.BeginForm("Create", "Alumno", FormMethod.Get, new {id="fTest", @class="formulario-ua"})

El resultado final sería

<form action="/Alumno/Create" class="formulario-ua" id="fTest" method="get"></form>

En caso de que no usemos using en la declaración de beginform deberemos usar endform para indicar

donde acaba.

@{ Html.BeginForm("Create", "Alumno", FormMethod.Get, new {id = "fTest", @class = "formulario-ua"}); } … @{ Html.EndForm();}

Yo usaré en todos los ejemplos using porque queda el código más agrupado.

Ahora es el momento de incluir elementos en el formulario

Page 13: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

13

Label(s:name, o:text)

Un etiqueta con texto que hace referencia a un campo (name). En caso de que no se indique el texto

pondrá por defecto el nombre del campo que hayamos indicado en el primer parámetro.

@using(Html.BeginForm("Create", "Alumno", FormMethod.Get, new {id = "fTest", @class = "formulario-ua"})) { @Html.Label("Nombre", "Nombre:") … }

En este ejemplo mostrará una etiqueta “Nombre:” que hace referencia a un campo “Nombre”.

<label for="Nombre">Nombre:</label>

TextBox(s:name, o:value)

Crea una caja de texto con el nombre que le indiquemos y con un valor por defecto en el segundo

parámetro.

@Html.TextBox("Nombre", "Alberto")

genera

<input id="Nombre" name="Nombre" type="text" value="Alberto" />

CheckBox(s:name, b:checked)

Genera una elemento checkbox.

DropDownList(s:name, list:selectlistitems)

Genera una lista desplegable en la que podemos seleccionar un único elemento.

@Html.Label("Sexo") @Html.DropDownList("Sexo", new MultiSelectList(new[] {"Hombre", "Mujer"}))

Genera

Hidden(s:name, o:value)

Genera un campo oculto.

Todo el contenido que se asigne en el valor por defecto (en cualquier HTMLHelper) se codifica

automáticamente para evitar que se produzcan ataques XSS injection.

Page 14: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

14

ListBox(s:name, list:selectlistitems)

Genera una lista de valores en la que podemos seleccionar más de un elemento.

@using(Html.BeginForm("Create", "Alumno", FormMethod.Get, new {id = "fTest", @class = "formulario-ua"})) { @Html.Label("Unidad") @Html.ListBox("Unidad", new MultiSelectList(new[] {"Servicio de Informática", "Selección y Formación", "Servicio de Personal"})) }

Genera

RadioButton(s:name, o:value, b:checked)

Genera una elemento radiobutton

TextArea(s:name, s:value)

Crea una caja de texto de tipo textarea.

ValidationSummary([Exclude property-level error])

Muestra una lista no ordenada de todos los errores que se producen al validar el formulario.

Se puede validar todo o excluir los errores a nivel de las propiedades del modelo

Los errores se pueden lanzar en tiempo de ejecución con la propiedad AddModelError(campo, mensaje

de error) del objeto ModelState.

En caso de que el campo lo dejemos vacío estamos lanzando un error a nivel de modelo

ModelState.AddModelError("", "Prueba de un error general");

y si indicamos el campo lo hacemos a nivel de propiedad.

ModelState.AddModelError("Nombre", "El nombre no cumple con los requisitos");

Añadimos a la vista un sumario de validación

@using(Html.BeginForm()) { @Html.ValidationSummary(false) }

Page 15: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

15

El resultado

Por defecto asigna el estilo "validation-summary-errors”.

ValidationMessage (s:[Nombre del campo], o:[Mensaje de error])

En caso de que no queramos que sea un sumario el que recoja todos los mensajes, si no que cada

mensaje aparezca en el punto que indiquemos (normalmente a la derecha del campo), usaremos este

Helper.

Si no se especifica el mensaje de error, todos aquellos errores que se produzcan (o provoquemos) se

visualizarán en este punto.

@Html.ValidationMessage("Nombre")

Se visualizará de la siguiente manera

Por defecto asigna el estilo “field-validation-error”.

Action(s: [nombre acción])

Nos permite llamar a un método / acción de un controlador. Puede parecerse mucho a las vistas

parciales que vimos ayer y que recordaremos luego, pero lo cierto es que mientras las vistas parciales

están pensadas para escribir bloques de código, action está orientada a ejecutar el proceso completo

de la acción de un controlador (que incluye la generación del código con la Vista).

El resultado es una cadena de texto con todo el contenido generado.

@Html.Action("Cabecera")

ActionLink(s: [descripción], s: [acción], s: [controlador])

Permite generar enlaces a acciones determinadas de un controlador. Por ejemplo si queremos poner

un enlace a la acción Index del Home usaríamos

Page 16: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

16

@Html.ActionLink("Página principal", "Index", "Home")

Se usa en las plantillas para realizar cualquier acción con el modelo del controlador, alta, baja, edición

o borrado.

Dispone de muchas sobrecargas este Helper, permitiendo desde indicar protocolor, servidor y ancla,

hasta definir los atributos HTML.

RouteLink(s: [descripción], d: [valores ruta])

Es parecido alterior, porque genera un enlace a una ruta o una acción de un controlador. Es algo más

artesanal ya que no dispone de tantas sobrecargas y todos los valores se meten en un campo o se

llama a la routa por su nombre (en caso que se haya definido previamente). Si queremos enlazar con

la acción “Acerca de” usaríamos

@Html.RouteLink("Acerca de", new { controller = "Home", action="About"})

RenderAction(s: [nombre acción])

Es idéntica a Action con la diferencia de que no almacena el contenido en una cadena de texto si no

que la escribe directamente al objeto Response, con lo que se visualiza por el navegador.

Aunque puede parecer que crear un Helper es lo mismo que llamar a vistas parciales (que vimos ayer)

porque ambas se usan para reaprovechar código o dejarlo más estructurado, si que es cierto que cada

uno tiene su uso.

Helpers personalizado está pensado para pequeños trozos de código, que generan una programación

sencilla y que se comparte con diferentes vistas de tu proyecto o incluso entre varios.

Partial views están orientadas a secciones de código, con el objetivo de hacer más clara la estructura.

Puede contener una programación tan complicada como la vista que les llama.

Disponemos de dos HTMLHelpers dedicados a trabajar con Partial views (ayer usamos el comando

RenderPage).

Partial(s: nombrevista)

Genera una cadena de texto con la ejecución de la vista parcial

Si deseamos que una acción sea sólo llamada desde Action o RenderAction pero no directamente

como una dirección más en el navegador podemos usar la anotación ChildActionOnly antes de la

declaración

[ChildActionOnly]

public ActionResult Cabecera() {

}

Page 17: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

17

@Html.Partial("_Cabecera")

RenderPartial(s: nombrevista)

Es idéntica a Partial con la diferencia de que no almacena el contenido en una cadena de texto si no

que la escribe directamente al objeto Response, con lo que se visualiza por el navegador.

@{ Html.RenderPartial("_Cabecera"); }

Personalizados

Como es lógico MVC nos permite crear nuestros propios Helpers para darle mayor potencia a éstos.

Se comportan como una función a la que se pasan parámetros si los necesita, y dentro genera el código

que queremos mostrar.

Helpers locales declarativos (inline helpers)

El formato es @Helper [Nombre Función]( [parámetros] )

@helper BreadCumb(string[] elementos) { <div> for(int i=0; i < elementos.Count(); i++) { <span>@elementos[i]</span> if (i < elementos.Count() - 1) { <text>></text> } } </div> }

Luego para llamarla @NombreFunción(parámetros)

@BreadCumb(new[] {"Inicio", "Administración", "Secciones"})

El resultado es el siguiente

Es costumbre a la hora de poner los parámetros, anteponer el nombre de cada parámetro y luego :

(dos puntos).

@BreadCumb(elementos: new[] {"Inicio", "Administración", "Secciones"})

Si deseamos que es helper sea reutilizables desde cualquier vista, añadimos la carpeta App_Code a

nuestro proyecto (no aparece como opción en las carpetas de ASP.NET) y creamos el fichero

BreadCumbHelpers.cshtml. Copiamos el código del Helper y lo guardamos.

Page 18: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

18

Ahora para hacerle referencia desde la vista llamaremos al helper de la siguiente manera

@[Nombre fichero (sin extensión)].[Nombre del helper o función]( [parámetros])

@BreadcumbHelpers.BreadCumb(elementos: new[] { "Inicio", "Administración", "Secciones" })

Como resumen de los helpers locales:

Se declaran en la propia vista en un bloque @helper

No pueden devuelven ningún tipo de dato.

En realidad devuelven un HelperResult pero para nosotros es totalmente transparente.

Su código se escribe directamente en la vista

Sirven exclusivamente para generar HTML (a diferencia de los helpers locales normales que

podían devolver cualquier tipo de dato).

Helpers globales (external helper)

Hay otra forma de crear Helpers personalizados en el que “construimos el contenido” que queremos

generar. Será una clase, con métodos que no generan HTML directamente como una vista parcial, si

no que devuelve un objeto de tipo IHtmlString. Las etiquetas se generan con TagBuildery los atributos

se añaden con MergeAttribute.

Un ejemplo muy útil, y que encontramos en muchas páginas, es crear nuestro propio ActionLink para

trabajar con imágenes.

using System.Web; using System.Web.Mvc; using System.Web.Mvc.Html; using System.Web.Routing; namespace _3_MVCHelpers.Helpers { public static class HtmlImageActionLinkHelper { public static IHtmlString ImageActionLink( this HtmlHelper helper, string imageUrl, string actionName, object routeValues, object htmlAttributes ) { var builder = new TagBuilder("img"); builder.MergeAttribute("src", imageUrl); builder.MergeAttributes(new RouteValueDictionary(htmlAttributes)); var link = helper.ActionLink("[replaceme]", actionName, routeValues); var html = link.ToHtmlString().Replace("[replaceme]", builder.ToString(TagRenderMode.SelfClosing)); return new HtmlString(html); } } }

Para referenciarlo en nuestra propia vista, usaremos @Html.[Método] ([Parámetros]).

Page 19: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

19

Si queremos añadir una imagen 012.jpg que al pulsar sobre ella vaya a la acción Index usaríamos: @Html.ImageActionLink( Url.Content("~/Fotos/012.jpg"), "Index", new { id = 5 }, new { id = "imgnb", width = "100px", height = "150px", alt = "Foto playa de Alicante" } )

Como resumen de los helpers globales:

Método de extensión de la clase HtmlHelper.

Devuelve una instancia de HtmlString.

o En cualquier caso, no es obligatorio que un helper devuelve siempre código HTML,

también podría devolver cualquier otro tipo de datos, por ejemplo un bool o

simplemente no devolver nada (void). Además incluso podría devolver directamente

un string y entonces Razor codificaría en HTML la salida (con HtmlString, Razor confía

en los helpers y no codifica en HTML la salida).

o Utilizar la clase TagBuilder para construir el DOM.

Accesible por cualquier vista que importe el espacio de nombres donde esté declarado el

helper (también pueden incluir el espacio de nombres en el fichero Views/Web.config y estará

automáticamente disponibles para todas las vistas).

GENERACIÓN DE VERSIONES IDIOMÁTICAS

CONFIGURAR Y DETECTAR EL IDIOMA POR DEFECTO

La plantilla que disponemos como guía dispone de una gestión para detectar el idioma. Dispone de un la parte superior derecha un menú para cambiar de idioma

Seleccionando otro idioma veremos que los elementos comunes han cambiado.

La lógica se gestiona desde Application_AcquireRequestState en el fichero Global.asax.cs.

Analiza si ya la tenemos guardada en Session[“idioma”]. En caso de que no la encuentre la extrae de

la configuración del navegador.

Page 20: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

20

Dentro de la carpeta Controller disponemos de la lógica básica para cambiar de idioma y retornar a la

página que nos llamó.

RECURSOS

El elemento base para gestionar las traducciones son los recursos.

Una buena práctica es crearnos una carpeta Resources y meter todos aquellos ficheros que

necesitemos. Se pueden crear a nivel de controlador o modelo o a nivel de aplicación si nuestro

proyecto es muy básico.

Sobre el proyectos pulsamos botón derecho Agregar > Nueva carpeta y le ponemos el nombre

Resources.

Ahora sobre esta nueva carpeta Agregar > Nuevo elemento … y seleccionamos (o filtramos) Archivo de

recursos. Le llamamos modelos.resx

Añadimos las descripciones que queremos que estén en varios idiomas

Es importante que marquemos el fichero como público para que se pueda acceder desde el resto de

los elementos de MVC

Page 21: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

21

Para crear la versión de recursos para otro idioma, copiamos y pegamos el que usemos de base y luego

le añadimo .[dos digitos del idioma] antes de la extensión del fichero.

Es nuestro caso para crear el fichero de recursos en inglés renombraríamos copia de modelos.resx por

modelo.en.resx y traduciríamos los valores de cada una de las etiquetas.

VISTAS

La manera más cómoda de pasar textos traducidos a las vistas, en caso de que sean pocos, es usar el

controlador y el objeto ViewBag. Para acceder a un recurso escribimos el [nombre carpeta de

recursos].[ nombre recurso (sin extensión].etiqueta.

ViewBag.Titulo = Resources.modelos.tituloLabel;

Luego en la propia vista lo referenciamos

Texto del fichero de recursos: @ViewBag.Titulo<br />

Si la vista contiene muchos elementos a traducir, lo más sencillo es crear dos versiones de la vista de

la misma manera que lo hemos hecho con el fichero de recursos. Cogemos la vista base index.cshtml

la copiamos y la pegamos y renombramos por index.en.cshml. Hacemos los cambios que corresponda

Creamos una clase para gestionar los idiomas CultureHelper. La variable Cultures almacena los idiomas

con los que trabajemos. El primero de ellos será el que se usará por defecto en caso de que detectemos

otro que no se corresponda con nuestro listado.

using System; using System.Collections.Generic; using System.Linq; namespace _3_MvcGlobalization.Helpers { public static class CultureHelper { // Include ONLY cultures you are implementing as views private static readonly Dictionary<String, bool> Cultures = new Dictionary<string, bool> { {"es", true}, // first culture is the DEFAULT {"en", true}, {"ca", true} }; /// <summary> /// Returns a valid culture name based on "name" parameter. If "name" is not valid, it returns the default culture "en-US" /// </summary> /// <param name="name">Culture's name (e.g. en-US)</param> public static string GetValidCulture(string name) { if (string.IsNullOrEmpty(name)) return GetDefaultCulture(); // return Default culture if (Cultures.ContainsKey(name)) return name;

Page 22: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

22

// Find a close match. For example, if you have "en-US" defined and the user requests "en-GB", // the function will return closes match that is "en-US" because at least the language is the same (ie English) foreach (var c in Cultures.Keys) if (c.StartsWith(name.Substring(0, 2))) return c; // else return GetDefaultCulture(); // return Default culture as no match found } /// <summary> /// Returns default culture name which is the first name decalared (e.g. en-US) /// </summary> /// <returns></returns> public static string GetDefaultCulture() { return Cultures.Keys.ElementAt(0); // return Default culture } /// <summary> /// Returns "true" if view is implemented separatley, and "false" if not. /// For example, if "es-CL" is true, then separate views must exist e.g. Index.es-cl.cshtml, About.es-cl.cshtml /// </summary> /// <param name="name">Culture's name</param> /// <returns></returns> public static bool IsViewSeparate(string name) { if (Cultures.ContainsKey(name)) return Cultures[name]; return false; } } }

El siguiente paso es crear nuestro propio controlador que detectará el idioma y personalizará la vista.

Requerimos hacer uso de dos métodos de la clase Controller: ExecuteCore y OnActionExecuted.

El primero normaliza el idioma, lo almacena en una variable sesión y establece CurrentCulture.

En Session[“idioma”] vamos a almacenar el idioma que se haya detectado o el que se seleccione (lo

veremos luego). De esa manera lo podremos usar en cualquier vista o controlador.

El segundo establece la vista que debe abrir el controlador dependiendo del idioma que se haya

seleccionado.

using System.Globalization; using System.Threading; using System.Web.Mvc; using _3_MvcGlobalization.Helpers; namespace _3_MvcGlobalization.Controllers { public class UaController : Controller { protected override void OnActionExecuted(ActionExecutedContext filterContext) { // Detectamos si llamamos desde una vista var view = filterContext.Result as ViewResultBase;

Page 23: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

23

if (view == null) // En caso de que no sea, salims return; string cultureName = Thread.CurrentThread.CurrentCulture.Name; // Buscamos si if (cultureName == CultureHelper.GetDefaultCulture()) return; // Are views implemented separately for this culture? if not exit bool viewImplemented = CultureHelper.IsViewSeparate(cultureName); if (viewImplemented == false) return; string viewName = view.ViewName; int i; if (string.IsNullOrEmpty(viewName)) viewName = filterContext.RouteData.Values["action"] + "." + cultureName; // Index.en-US else if ((i = viewName.IndexOf('.')) > 0) { // contains . like "Index.cshtml" viewName = viewName.Substring(0, i + 1) + cultureName + viewName.Substring(i); } else viewName += "." + cultureName; // e.g. "Index" ==> "Index.en-Us" view.ViewName = viewName; filterContext.Controller.ViewBag._culture = "." + cultureName; base.OnActionExecuted(filterContext); } protected override void ExecuteCore() { var idioma = Session["idioma"]; string cultureName; if (idioma != null) cultureName = idioma.ToString(); else { cultureName = (Request.UserLanguages == null ? CultureHelper.GetDefaultCulture() : Request.UserLanguages[0]); if (cultureName.IndexOf("-") > 0) cultureName = cultureName.Substring(0, cultureName.IndexOf("-")); Session["idioma"] = cultureName; } // Normalizamos var normalizedCultureName = CultureHelper.GetValidCulture(cultureName); if (normalizedCultureName != cultureName) { cultureName = normalizedCultureName; Session["idioma"] = cultureName; } // Actualizamos el idioma Thread.CurrentThread.CurrentCulture = CultureInfo.CreateSpecificCulture(cultureName); Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(cultureName); base.ExecuteCore(); }

Page 24: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

24

} }

Page 25: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

25

PLANTILLA

Por defecto la plantilla que se usa es la que se configure en /Views/ _ViewStart.cshtml.

Por seguir con este criterio, si modificamos este fichero y usamos la variable Session[“idioma”]

tendremos la plantilla que se debe usar.

@{ Layout = "~/Views/Shared/_Layout." + @Session["idioma"] + ".cshtml"; }

En clase lo optimizaremos para que no se produzcan errores cuando no esté definida esta variable.

CAMBIAR DE IDIOMA

Nuestra plantilla permite cambiar el icioma

public ActionResult ChangeLanguage(string language) { Session["idioma"] = language; if (Request.UrlReferrer != null) return Redirect(Request.UrlReferrer.ToString()); return Redirect("Index"); }

[ @Html.ActionLink("English", "ChangeLanguage", "Home", new { language = "en" }, null) ] [ @Html.ActionLink("Español", "ChangeLanguage", "Home", new { language = "es" }, null) ] [ @Html.ActionLink("Valencià", "ChangeLanguage", "Home", new { language = "ca" }, null) ]

En caso de que nos envíen un idioma que no se corresponda con el listado admitido, no habrá

problemas porque en la siguiente llamada a Index (o la página desde donde se llamó) se detectará que

no se corresponde con uno de los admitidos y se asignará el que tengamos por defecto.

MODELO

Siguiendo el ejemplo del libro de antes, si queremos que la descripción del título salga del fichero de

recursos remplazamos

[Display(Name = "Título del libro")] public string Titulo { get; set; }

por

[Display(Name = "tituloLabel", ResourceType = typeof(Resources.modelos))] public string Titulo { get; set; }

En caso de que nos de un error de que no se encuentra un recurso público con ese nombre, recordar

lo de marcar Public en el fichero de recursos.

Page 26: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

26

BOOTSTRAP

Es un framework diseñado para simplificar el proceso de creación de diseños web. Para ello nos ofrece

una serie de plantillas CSS y de ficheros JavaScript, los cuales nos permiten conseguir: Interfaces que funcionen de manera brillante en los navegadores actuales, y correcta en los

no tan actuales.

Un diseño que pueda ser visualizado de forma correcta en distintos dispositivos y a distintas

escalas y resoluciones.

Una mejor integración con tus las librerías que sueles usar habitualmente, como por ejemplo

jQuery.

Un diseño sólido basado en herramientas actuales y potentes como LESS o estándares como

CSS3/HTML5

Vamos a trabajar durante el curso con la versión 2.3.2 aunque ya está disponible la versión 3. En el

momento que sea más estable y la mayoría de los componentes que usamos sean compatibles

haremos el salto a la nueva versión.

Nada mejor que acceder a su página web y ver lo que nos ofrece http://getbootstrap.com/2.3.2/

De todos los elementos nos vamos a centrar en los básicos para comenzar a trabajar:

Grid (http://getbootstrap.com/2.3.2/scaffolding.html#fluidGridSystem)

Botones (http://getbootstrap.com/2.3.2/base-css.html#buttons)

Formularios (http://getbootstrap.com/2.3.2/base-css.html#forms)

Iconos (http://getbootstrap.com/2.3.2/base-css.html#icons)

Page 27: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

27

JQUERY

jQuery es una biblioteca de JavaScript, que permite simplificar la manera de interactuar con los

documentos HTML, manipular el árbol DOM, manejar eventos, desarrollar animaciones (FLV) y agregar

interacción con la técnica AJAX a páginas web. Es la biblioteca de JavaScript más utilizada.

ASP.NET MVC usa esta librería de base (la podemos encontrar en la carpeta Scripts) y la mayoría de los

plugins que encontramos por Internet hace uso de ella.

La plantilla que tiene por defecto ASP.NET MVC la incluye con lo que podemos utilizarla en nuestras

vistas sin ningún problema.

La tarea más común en JQuery es acceder a algún elemento de nuestra página modificar sus

propiedades o contenido y que se actualice antes de que se visualice la página al usuario.

Nos vamos a centrar en estos puntos y cada día iremos incorporando nuevas características.

SELECTORES

Jquery dispone de varios métodos para acceder a los elementos de nuestra página. Vamos a analizar

los más comunes. Todos ellos utilizan la función $(“[selector]”). Si nunca se ha programado con JQuery

o Mootools nos llamará la atención que se use el $ como función para acceder a los elementos de

nuestra página.

Vamos a analizar los selectores más comunes

$(“#id”)

Seleccionamos un elemento HTML por el id que tenga. Es muy normal usarlo en elementos muy

comunes de nuestra página cabecera, cuerpo, noticias o pie, aunque si somos cuidadosos con los ids,

podemos usarlo en cualquier elemento que queramos.

Por ejemplo si tenemos una capa div con id igual a capa_1

<div id="capa_1"></div>

Para acceder a este elemento usamos

var el = $("#capa_1");

En caso de que trabajemos con JQuery y Mootools, y hagamos referencia a ambas librerías desde

nuestras páginas, se producirá un conflicto por la función $ que ambas usan. Para solucionarlo

JQuery ofrece una solución muy sencilla.

Incluimos la instrucción jQuery.noConflict(); para indicar que desde este momento para hacer uso

del selector en JQuery vamos a utilizar jQuery (“[selector]”) en vez de $(“[selector]”).

De esa manera ya no interfiere con Mootools que lo sigue utilizando sin problemas.

Page 28: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

28

Ahora podríamos hacer cualquier operación con este elemento, que es un objeto que dispone de

métodos / funciones que iremos viendo.

$(“elemento”)

En ocasiones nos interesa que todos los elementos HTML de un tipo (por ejemplo los enlaces) cambien

alguna propiedad que no es accesible (el ejemplo más claro es que se abran en un nueva ventana).

Tenemos un listado de enlaces

<div id="capa_2"> <a href="1">Enlace 1</a><br /> <a href="2">Enlace 2</a><br /> <a href="3">Enlace 3</a><br /> <a href="4">Enlace 4</a><br /> </div>

Para acceder al listado de enlaces usamos el selector por elemento

var els = $("a");

y para recorrer todos los elementos para actualizar alguna propiedad

els.each(function () { var el = $(this); el.attr("target", "_blank"); });

Un error común cuando comenzamos con JQuery es que creemos que el elemento “el” es el propio

elemento HTML y que por tanto accedo a sus atributos con el.target = "_blank";. Si lo probáis veréis

que no es así, porque “el” es un objeto JQuery y no un enlace. Debemos usar los métodos que nos

ofrece JQuery para estas tareas.

$(“.clase”) o $(“elemento.clase”)

Un paso más en la selección es que no accedamos a elementos tan genéricos si no a aquellos que

nosotros marquemos con un estilo determinado. El ejemplo anterior sería mejor si sólo lo aplicáramos

a aquellos enlaces que pertenezcan a la clase “externo”.

Modificamos el listado anterior para indicar que dos son externos y otros dos no.

<div id="capa_2"> <a class="externo" href="1">Enlace 1</a><br /> <a href="2">Enlace 2</a><br /> <a class="externo" href="3">Enlace 3</a><br /> <a href="4">Enlace 4</a><br /> </div>

Para acceder a estos dos enlaces no podemos usar el genérico de elementos porque cogeríamos los 4,

usamos:

var els = $("a.externo");

o en caso de que sólo se use esta clase con enlaces y no haya confusión con otros elementos

var els = $(".externo");

Page 29: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

29

Otro ejemplo muy común es crearnos un estilo “obligatorio” que realice determinadas operaciones

sobre los elementos (cambiar color, poner en negrita, añadir un asterisco para indicar que es

obligatorio, etc.).

var els = $(".obligatorio");

y luego los recorremos

els.each(function () { var el = $(this); // Operaciones sobre cada elemento });

Hijos o descendente

Ahora es el momento de combinar selectores

$(“#cabecera a”)

Selecciona todos los enlaces que hay dentro de el elemento con id igual a “cabecera” da lo mismo que

estén en el siguiente nivel de “cabecera” o dentro de otros elementos. En

<div id="cabecera" style="margin-top: 20px;"> <a href="1">Enlace 1</a><br /> <a href="2">Enlace 2</a><br /> <div id="subcabecera" style="margin-top: 10px;"> <a href="3">Enlace 3</a><br /> <a href="4">Enlace 4</a><br /> </div> </div>

Cambiaría el color a los 4 enlaces

var els = $("#cabecera a"); els.each(function () { var el = $(this); el.attr("style", "color: red"); });

$(“#cabecera > a”)

Si solo queremos modificar los 2 enlaces hijo y descartar otros descendientes que pertenecen a otro

elemento.

var els = $("#cabecera > a"); els.each(function () { var el = $(this); el.attr("style", "color: red"); });

Sólo cambia el color a los dos primeros enlaces que son hijos directos de “cabecera”.

Page 30: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

30

FUNCIONES

Un problema que nos podemos encontrar con JavaScript es el momento de inicializar los elementos

de HTML porque hasta que no se acaba el código, no tenemos a nuestra disposición a todos los

elementos.

Una buena costumbre es poner al final del HTML todos los ficheros que hacen referencia a JavaScript.

La razón principal es que la persona ya puede comenzar a visualizar la página en ese momento y no

debe esperar a que se carguen todos los ficheros JavaScript que en ocasiones, si hacen referencia a

direcciones externas, pueden producir un retardo molesto.

Además de esta técnica que usaremos en nuestras plantillas, jQuery tiene dos métodos de ejecutar

código en el momento que el Modelo de Objetos del Documento (DOM) está disponible:

$(document).ready

http://api.jquery.com/ready/

Le indicamos la función que se ejecutará en el momento de estar listo el DOM.

En el siguiente ejemplo actualizará el contenido de un elemento con id igual a “capa_1”. Independiente

de que este código esté al principio o al final no dará error porque no se ejecuta en el momento de

leerse el JavaScript.

$(document).ready(function () { var el = $("#capa_1"); el.html("Añadimos un texto"); });

Si el código fuera sólo var el = $("#capa_1"); el.html("Añadimos un texto");

No funcionaría al principio de la página porque aun no está disponible el elemento “capa_1”.

$(function () { });

Tiene el mismo comportamiento que la anterior. Cuando se pasa una función como primer parámetro,

le indicas a jQuery que lo ejecute cuando esté disponible el DOM. El ejemplo anterior sería:

$(function () { var el = $("#capa_1"); el.html("Añadimos un texto"); });

Arrays

Aplicar una función a un array es una tarea muy común. Lo hemos visto cambiando el comportamiento

de los enlaces. Se usa mucho para asignar eventos que no por accesibilidad no están permitidos dentro

del código HTML.

Usamos el comando each (http://api.jquery.com/jQuery.each/) que le pasamos una función como

parámetro y dentro de ésta podemos acceder a cada elemento con $(this).

arrayElementos.each(function () { var el = $(this);

Page 31: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

31

// Operaciones sobre cada elemento });

Selectores por función

.parent()

Obtiene el padre directo de un elemento.

En la siguiente figura vemos una imagen dentro de un div. Si tenemos seleccionado la imagen y

solicitamos su padre obtenemos la capa div.

.children()

Obtiene los hijos inmediatos únicos de un elemento.

En la siguiente figura vemos una capa div con tres enlaces dentro. Si tenemos seleccionada la capa siv

y solicitamos los hijos obtenemos un array de enlaces, que podemos gestionar facilmente con each.

CONTENIDO

Disponemos dos formas muy sencillas para modificar el contenido de un elemento.

html

http://api.jquery.com/html/

Nos deja remplazar el código o texto que hay en ese el elemento por el que le indiquemos. Permite

código con etiquetas HTML.

el.html("Añadimos un texto en <strong>negrita</strong>");

La capa pasa a tener el siguiente código

<div id="capa_1">Añadimos un texto en <strong>negrita</strong></div>

Page 32: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

32

text

http://api.jquery.com/text/

Parecido al anterior pero sólo para remplazar con texto sin formato. Ambas funciones también

permite leer el contenido si no se le envía ningún parámetro. En el caso de text, si lo que lee tiene

etiquetas HTML las elimina.

var texto = el.text();

val

http://api.jquery.com/val/

Devuelve o asigna el valor a un campo de un formulario.

var contenido = el.val(); el.val(contenido);

append

http://api.jquery.com/append/

En caso de que el elemento ya tenga contenido, no lo remplaza, lo escribe detrás del contenido actual.

prepend

http://api.jquery.com/prepend/

En caso de que el elemento ya tenga contenido, no lo remplaza, lo escribe antes del contenido actual.

load

http://api.jquery.com/load/

Podemos cargar el contenido desde otra página. Lo normal, y como ya hicimos el 2º día es que lo

hagamos desde una acción de nuestros controladores.

Por ejemplo si queremos cargar el contenido de la acción Contenido de nuestro controlador Home,

ejecutaríamos:

el.load("/Home/Contenido");

Si la acción hace algo tan básico como public string Contenido() { return "Este es el texto que devuelve el action Contenido"; }

El resultado es

Page 33: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

33

.css()

Consultamos o modificamos los estilos del elemento.

Por ejemplo si queremos cambiar el color de un texto a rojo para resaltarlo

PROPIEDADES

attr

http://api.jquery.com/attr/

En ocasiones lo que nos interesa no es añadir contenido si no modificar alguna propiedad, por ejemplo

el color o poner en negrita por si queremos destacar algo.

el.attr("style", "color: red; font-weight: bold;");

y el resultado es visible en la etiqueta.

prop

http://api.jquery.com/prop/

Aunque en muchas ocasiones nos pueda llevar a confusión con la function attr, prop está orientada a

modificar propiedades de los objetos como puedes ser checked, disabled, multiple, readOnly, etc.,

mientras que attr a modificar atributos como class, href, label, src, title, etc.

Por ejemplo si queremos consultar o modificar el estado de un checkbox

$(elemento).prop("checked");

Y

$(elemento).prop("checked", true);

Page 34: ASP.NET MVC 4 - si.ua.es · Escribe el contenido que le pasemos sin codificar (que es lo que hace por defecto ASP.NET MVC 3). Puede que en ocasiones necesitemos que sea así (por

ASP.NET MVC 4 | ELEMENTOS GRÁFICOS

Andrés Vallés Botella | Analista | Desarrollos propios Servicio de Informática | Universidad de Alicante Campus de Sant Vicent del Raspeig | 03690 | España http://si.ua.es/es

34

EJERCICIOS

Reemplazar contenido de un div con lo insertado en un textarea

Añadir el contenido de un textarea a un div

Chequear todos los checkbox que hay dentro de una capa div

Igualar altura de todas las columnas que haya dentro de un capa div. Usaremos el método

height()

Añadir un icono delante de todos los enlaces que tengan la clase vineta

ANUNCIOS

Crear un helper para poder valorar un anuncio

Crear un helper para poder realizar comentarios

CATALOGADOR

Crear helpers para los elementos comunes

o Descripción de un catalogador

o Descripción de una sección