La Electricidad Y La Electrónica Trabajo Tecnología.pdf
Frontal avanzado y assetic
1.
2.
3. ¿Quién Soy?
•Tech Lead en Ofertix.com
•Apasionado de la Web
•7 años en PHP
•Enganchado a Symfony desde la 1.2
•‘Whovian’ y Aerotrastornado
miquel@solilokiam.com
@solilokiam
http://www.github.com/solilokiam
7. ¿Qué es Ofertix?
•Vendemos productos y servicios por internet
•A precios interesantes
•Tenemos varias lineas de negocio
8. ¿Qué es Ofertix?
•Vendemos productos y servicios por internet
•A precios interesantes
•Tenemos varias lineas de negocio
•Ventas Privadas, Ocio, Full Price yTienda Física
9. ¿Qué es Ofertix?
•Vendemos productos y servicios por internet
•A precios interesantes
•Tenemos varias lineas de negocio
•Ventas Privadas, Ocio, Full Price yTienda Física
•7 años en marcha
10. ¿Qué es Ofertix?
•Vendemos productos y servicios por internet
•A precios interesantes
•Tenemos varias lineas de negocio
•Ventas Privadas, Ocio, Full Price yTienda Física
•7 años en marcha
•Principalmente Symfony 1.2
24. Pero...
•Nuestra interfaz móvil es mejorable
•Queremos añadir full-text search
•Queremos mejorar lineas de negocio
•Ya toca un lavado de cara
25. Pero...
•Nuestra interfaz móvil es mejorable
•Queremos añadir full-text search
•Queremos mejorar lineas de negocio
•Ya toca un lavado de cara
•Y de cuerpo
40. La remodelación del site tiene muchos temas interesantes
•Cache
•Reverse Proxy
•No-SQL
•Full-text Search
•UX
•Gestión de sesiones
•Recolección de datos
•Big Data
•Socialización
•Web Services
•Javascript Avanzado (MVC)
•Gestión de Statics
•Colas
•Optimización de Carga
•Balanceo de pagos
•...
50. •Una plantilla por tipo de device a cubrir.
•Una hoja de estilos por device*
•Un “Javascript” por device*
•Detectamos el tipo de device al servir el site
•Permitimos cambiar el tipo de plantilla servida.
Mobile DesignDevice Centric Design
51. Como lo hacemos
<?php
namespace SolilokiamRequestListenerBundleEventListener;
use SymfonyComponentHttpKernelHttpKernelInterface;
use SymfonyComponentHttpKernelEventGetResponseEvent;
use SolilokiamRequestListenerBundleDetectorDeviceDetector;
class RequestListener
{
public function onKernelRequest(GetResponseEvent $event)
{
$detector = new DeviceDetector();
$request = $event->getRequest();
$user_agent = $request->headers->get('user-agent');
if($detector->isMobile($user_agent))
{
$request->setRequestFormat('mobile', 'text/html');
} elseif($detector->isGameConsole($user_agent)) {
$request->setRequestFormat('game', 'text/html');
} elseif($detector->isTv($user_agent)) {
$request->setRequestFormat('tv', 'text/html');
} else {
$request->setRequestFormat('html', 'text/html');
}
}
}
52. <?php
namespace SolilokiamRequestListenerBundleDetector;
class DeviceDetector
{
//Incomplete regexs just educational purpouse;
private $mobile_device_regex = '/(alcatel|amoi|android|avantgo|blackberry|benq|cell|cricket|docomo|elaine|htc|iemobile|iphone|ipad|ipaq|ipod|j2me|java|midp|mini|mmp|mobi|motorola|nec-|nokia|palm|panasonic|philips|phone|playbook|sagem|sharp|sie-|silk|smartphone|sony|symbian|t-mobile|telus|up.browser|up.link|vodafone|wap|webos|wireless|xda|xoom|zte)/i';private $game_console_device_regex = '/xbox/i';
private $tv_device_regex = '/(bravia|googletv)/i';
public function __construct()
{
}
public function isMobile($user_agent)
{
if(preg_match($this->mobile_device_regex,$user_agent))
{
return true;
}
else
{
return false;
}
}
public function isGameConsole($user_agent)
{
if(preg_match($this->game_console_device_regex,$user_agent))
{
return true;
}
else
{
return false;
}
}
public function isTv($user_agent)
{
if(preg_match($this->tv_device_regex,$user_agent))
{
return true;
}
else
{
return false;
}
}
}
Como lo hacemos
56. Buscamos Programadores
•Expertos en Symfony 2 y 1
•Motivados
•Con ganas de aprender y mejorar
•Incorporarse en un gran equipo
•Proyecto consolidado pero en mejora continua
•Buenas condiciones
Más Información: it@ofertix.com
http://alba-twist.blogspot.com.es/2011_10_01_archive.html
57. <?php
namespace SolilokiamRequestListenerBundleEventListener;
use SymfonyComponentHttpKernelHttpKernelInterface;
use SymfonyComponentHttpKernelEventGetResponseEvent;
use SymfonyComponentHttpKernelHttpKernel;
use SolilokiamRequestListenerBundleManagerDeviceRedirectManager;use SolilokiamRequestListenerBundleManagerDeviceManager;
class RequestListener
{
protected $device_manager;
protected $redirect_manager;
public function __construct(DeviceManager $device_manager,DeviceRedirectManager $redirect_manager){
$this->device_manager = $device_manager;
$this->redirect_manager = $redirect_manager;
}
public function onKernelRequest(GetResponseEvent $event)
{
if(HttpKernel::MASTER_REQUEST === $event->getRequestType())
{
$request = $event->getRequest();
$user_agent = $request->headers->get('user-agent');
$this->device_manager->detectDevice($user_agent);
$response = $this->redirect_manager->redirectIfNeeded($request);
if($response) $event->setResponse($response);
return;
}
}
}
Como lo hacemos (pero mejor)
58. Como lo hacemos (pero mejor)
<?php
namespace SolilokiamRequestListenerBundleManager;
use SolilokiamRequestListenerBundleDetectorDeviceDetector;
class DeviceManager
{
const DEVICE_MOBILE = 'mobile';
const DEVICE_GAME = 'game';
const DEVICE_TV = 'tv';
protected $session;
public function __construct($session)
{
$this->session = $session;
}
public function hasDevice()
{
return $this->session->has('device');
}
public function setDevice($device)
{
$this->session->set('device',$device);
}
public function getDevice()
{
return $this->session->get('device');
}
public function detectDevice($user_agent)
{
$detector = new DeviceDetector();
if($detector->isMobile($user_agent))
{
$this->setDevice(self::DEVICE_MOBILE);
} elseif($detector->isGameConsole($user_agent)) {
$this->setDevice(self::DEVICE_GAME);
} elseif($detector->isTv($user_agent)) {
$this->setDevice(self::DEVICE_TV);
}
}
}
59. <?php
namespace SolilokiamRequestListenerBundleManager;
//use SolilokiamRequestListenerBundleManagerDeviceManager;use SymfonyComponentHttpFoundationRedirectResponse;
class DeviceRedirectManager
{
const VIEW_MOBILE = 'mobile.desymfony.local';
const VIEW_GAME = 'game.desymfony.local';
const VIEW_TV = 'tv.desymfony.local';
protected $view_type;
protected $device_manager;
public function __construct(DeviceManager $manager)
{
$this->device_manager = $manager;
if(!$this->device_manager->hasDevice())
{
$this->view_type = '';
} else {
$device = $this->device_manager->getDevice();
$this->view_type = $device;
}
}
public function redirectIfNeeded($request)
{
$host = $request->getHost();
Como lo hacemos (pero mejor)
61. <?php
namespace SolilokiamRequestListenerBundleTwig;
use SymfonyBundleTwigBundleTwigEngine as BaseTwigEngine;
use SymfonyBundleFrameworkBundleTemplatingGlobalVariables;
use SymfonyComponentTemplatingTemplateNameParserInterface;
use SymfonyComponentConfigFileLocatorInterface;
use SolilokiamRequestListenerBundleManagerDeviceManager;
class TwigEngine extends BaseTwigEngine
{
protected $device_manager;
public function __construct(Twig_Environment $environment, TemplateNameParserInterface $parser,FileLocatorInterface $locator, DeviceManager $device_manager)
{
$this->device_manager = $device_manager;
parent::__construct($environment, $parser, $locator);
}
public function render($name, array $parameters = array())
{
$device = $this->device_manager->getDevice();
$device_template = preg_replace("/^w+:w+:/", '$0'.$device.'/', $name);
if ($this->exists($device_template)) {
$name = $device_template;
}
return parent::render($name, $parameters);
}
}
Como lo hacemos (pero mejor)
62. Como lo hacemos (pero mejor)
<?php
namespace SolilokiamFrontBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class DefaultController extends Controller
{
public function indexAction($name)
{
return $this->render('SolilokiamFrontBundle:Default:index.html.twig', array('name' => $name));}
}
64. Misión cumplida
•Faltaría switch entre vistas
•Mejor por cookies que por sesión
•URL’s y otras cosas configurables
http://www.vayagif.com/169459/claro-que-si-campeon-michael-jackson-estaria-orgulloso-de-ti
65. Misión cumplida
•Faltaría switch entre vistas
•Mejor por cookies que por sesión
•URL’s y otras cosas configurables
https://github.com/kbond/ZenstruckMobileBundle
https://github.com/suncat2000/MobileDetectBundle
http://www.vayagif.com/169459/claro-que-si-campeon-michael-jackson-estaria-orgulloso-de-ti
66. Ventajas
•Se ajusta mejor a las necesidades
•Facilidad de cambiar/hacer cosas especiales
•Más óptimo
Inconvenientes
•Mucho trabajo.
•Alta posibilidad de liarla parda.
•Múltiples url’s para la misma cosa
67. Responsive Design
•Una plantilla para todos los devices
•Una sola hoja de estilos
•Un solo javascript*
•La presentación se adapta al dispositivo
•Soporte a tantos devices como quieras*
68. ¿Qué es Responsive Design?
Responsive Web design is the
approach that suggests that
design and development should
respond to the user’s behavior
and environment based on screen
size, platform and orientation.
Kayla Knight @KaylaMaeKnight
81. ¿Y qué pasa con la tipografia?
Aplicamos la misma regla de cálculo
h1 {
font-size: 24px;
}
h1 a {
font-size: 11px;
}
24 / context = ¿?
11/ context = ¿?
82. ¿Y qué pasa con la tipografia?
El tamaño por defecto de la fuente suele ser 16px
83. ¿Y qué pasa con la tipografia?
El tamaño por defecto de la fuente suele ser 16px
Mejor lo seteamos en nuestro fichero de reset
84. ¿Y qué pasa con la tipografia?
El tamaño por defecto de la fuente suele ser 16px
body{
font-size:16px;
}
Mejor lo seteamos en nuestro fichero de reset
85. ¿Y qué pasa con la tipografia?
El tamaño por defecto de la fuente suele ser 16px
body{
font-size:16px;
}
Mejor lo seteamos en nuestro fichero de reset
body{
font-size: 100%;
}
86. ¿Y qué pasa con la tipografia?
El tamaño por defecto de la fuente suele ser 16px
body{
font-size:16px;
}
Mejor lo seteamos en nuestro fichero de reset
body{
font-size: 100%;
}
http://meyerweb.com/eric/tools/css/reset/
87. ¿Y qué pasa con la tipografia?
Aplicamos la misma regla de calculo
h1 {
font-size: 24px;
}
h1 a {
font-size: 11px;
}
88. ¿Y qué pasa con la tipografia?
Aplicamos la misma regla de calculo
h1 {
font-size: 24px;
}
h1 a {
font-size: 11px;
}
24 / 16 = 1.5
89. ¿Y qué pasa con la tipografia?
Aplicamos la misma regla de calculo
h1 {
font-size: 24px;
}
h1 a {
font-size: 11px;
}
24 / 16 = 1.5
11/ 16 = 0,6875
90. ¿Y qué pasa con la tipografia?
Aplicamos la misma regla de calculo
24 / 16 = 1.5
11/ 16 = 0,6875
h1 {
font-size: 1.5em;
}
h1 a {
font-size: 0.6875em;
}
91. Imágenes y media flexibles
Varias Opciones:
•Resize
•Crop
•HTML5 picture tag
•Clown Car
98. Clown Car<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 300 329" preserveAspectRatio="xMidYMid meet">
<title>Clown Car Technique</title>
<style>
svg {
background-size: 100% 100%;
background-repeat: no-repeat;
}
@media screen and (max-width: 400px) {
svg {
background-image: url(images/small.png");
}
}
@media screen and (min-width: 401px) and (max-width: 700px) {
svg {
background-image: url(images/medium.png);
}
}
@media screen and (min-width: 701px) and (max-width: 1000px) {
svg {
background-image: url(images/big.png);
}
}
@media screen and (min-width: 1001px) {
svg {
background-image: url(images/huge.png);
}
}
</style>
</svg>
•Buen soporte
•Buena con el ancho de banda
•Buena con el navegador
•Requiere de trabajo en el servidor
99. Media Queries
Desarrollado a partir de los MediaTypes (CSS 2)
@media screen {
body {
font-size: 100%;
}
}
@media print {
body {
font-size: 15pt;
}
}
100. Media Queries
@media screen and (min-width: 1024px) {
body {
font-size: 100%;
}
}
<link rel="stylesheet" href="wide.css" media="screen and (min-width: 1024px)" />
101. Media Queries
No solamente podemos filtrar por height o width:
width
height
device-width
device-height
orientation
aspect ratio
color (bit number)
color-index
monochrome(bits x pixel)
resolution (dpi)
scan(tv progressive o scan)
grid
102. Media Queries
No solamente podemos filtrar por height o width:
width
height
device-width
device-height
orientation
aspect ratio
color (bit number)
color-index
monochrome(bits x pixel)
resolution (dpi)
scan(tv progressive o scan)
grid
@media screen and (min-device-width: 480px) and (orientation: landscape) { ... }
104. Media Queries
Arreglar todas las cosas que no se acaban de adaptar con
Layout basado en un grid flexible
Cambiar tipografias
Modificar layout
Mostrar / Ocultar elementos
...
105. Ventajas
•Menos trabajo de crear vistas
•Menos posibilidad de liarla
•Mejor adaptabilidad ante nuevos devices
•Mejor SEO
Inconvenientes
•Mucho trabajo al maquetar
•No muy óptimo
109. Preprocesadores CSS
•Ahorro de muchas horas de maquetación
•Cambios Rápidos
•Código Estructurado
Assetic los integra perfectamente en nuestros proyectos.
118. Variables
@azul: #5B83AD;
@azul-claro: (@azul + #111);
#header { color: @azul-claro; }
#header { color: #6c94be; }
•Scope de las variables igual que CSS
•No han de ser declaradas antes de ser utilizadas
119. Variables
@azul: #5B83AD;
@azul-claro: (@azul + #111);
#header { color: @azul-claro; }
#header { color: #6c94be; }
•Scope de las variables igual que CSS
•No han de ser declaradas antes de ser utilizadas
@less-mola: "Less Mola";
@var: 'less-mola';
content: @@var;
120. Variables
@azul: #5B83AD;
@azul-claro: (@azul + #111);
#header { color: @azul-claro; }
#header { color: #6c94be; }
•Scope de las variables igual que CSS
•No han de ser declaradas antes de ser utilizadas
@less-mola: "Less Mola";
@var: 'less-mola';
content: @@var;
content: "Less Mola";
142. Funciones
escape(@string); // URL encodes a string
e(@string); // escape string content
%(@string, values...); // formats a string
ceil(@number); // rounds up to an integer
floor(@number); // rounds down to an integer
percentage(@number); // converts to a %, e.g. 0.5 -> 50%
round(number, [places: 0]);// rounds a number to a number of places
saturate(@color, 10%); // return a color 10% points *more* saturated
desaturate(@color, 10%);// return a color 10% points *less* saturated
lighten(@color, 10%); // return a color 10% points *lighter*
darken(@color, 10%); // return a color 10% points *darker*
149. Comentarios
/* Hola soy un comentario la mar de interesante */
.test_class { color: #008866 }
150. Comentarios
/* Hola soy un comentario la mar de interesante */
.test_class { color: #008866 }
/* Hola soy un comentario la mar de interesante */
.test_class { color: #008866 }
151. Comentarios
/* Hola soy un comentario la mar de interesante */
.test_class { color: #008866 }
/* Hola soy un comentario la mar de interesante */
.test_class { color: #008866 }
//Hola soy un comentario que mejor no salga en produccion
.test_class { color: #008866 }
152. Comentarios
/* Hola soy un comentario la mar de interesante */
.test_class { color: #008866 }
/* Hola soy un comentario la mar de interesante */
.test_class { color: #008866 }
//Hola soy un comentario que mejor no salga en produccion
.test_class { color: #008866 }
.test_class { color: #008866 }
155. Quiero saber más.
http://lesscss.org http://twitter.github.io/bootstrap/
http://lesshat.com/
¿Qué pasa con SASS?
•Más completo que less
•Peor documentación
•Mismos principios
•Hecho en ruby
•Ultimamente menos activo
156. Quiero saber más.
http://lesscss.org http://twitter.github.io/bootstrap/
http://lesshat.com/
¿Qué pasa con SASS?
•Más completo que less
•Peor documentación
•Mismos principios
•Hecho en ruby
•Ultimamente menos activo
http://sass-lang.com/
http://compass-style.org/
http://foundation.zurb.com/
157. Resumiendo
•Adaptad vuestra aplicación a varios devices
•Analizad vuestras necesidades
•Aplicad la técnica que mejor os vaya
•Utilizad preprocesadores de CSS