<?php
/**
  Clase Articulo
  @version 1.1
  Versión 1.1 ==> 15/Noviemb/2016 =>	Añadida función estática para buscar un producto por ean o código indistíntamente
  La clase artículo utilizará esta misma función para localizar el producto en el parámetro $ean
  Versión 2.0 ==> Vamos a optimizar las cargas de producto y las select que se utilizan aquí.
	Se cargará siempre el producto sin sus datos adicionales (escaparates asociados, temas, adjuntos, etc. Según el caso el diseñoador decidirá qué cargar.
	se hará una única carga por EAN y código y se cogerá el primero de los dos elementos_relacionados
 */
 
class SuperArticulo extends Apartado {
	public static $campos_tabla = array();
	public static $alias = '';
	public static $nombreTabla = '';
	public static $camposSelect = '';
	public static $whereSelect = '';
	public static $publicFieldList = array();


    public $codigo = 0;
    public $tipo = 0;
    public $nombre = 0;
    public $subtitulo = 0;
    public $stock = 0;
    public $pvp = 0;
    public $iva = 0;
    public $base = 0;
    public $ean = 0;
    public $referencia = 0;
    public $isbn = 0;
    public $autor = 0;
    public $fecha_alta = 0;
    public $num_paginas = 0;
    public $peso = 0;
    public $alto = 0;
    public $ancho = 0;
    public $ilustrador = 0;
    public $observaciones = '';
    public $fecha_ult_modif = 0;
    public $editorial = '';
    public $cod_editorial = 0;
    public $cod_distribuidor = 0;
    public $coleccion = 0;
    public $no_web = 0;
    public $familia = 0;
    public $familia_nombre = '';
	public $grupo_familia = 0;
    public $foto = 0;
    public $tema = '';
	public $tematica_restrictiva = '';		//Pedro 09/Septiembre/2019 ==> Temática más restrictiva para este artículo. La usamos para obtener los artículos asociados
    public $pvpoferta = 0;
    public $base_pvpoferta = 0;
    public $dto_maximo = 0;
    public $texto = 0;
    public $pvp_tar1 = 0;
    public $pvp_tar2 = 0;
    public $pvp_tar3 = 0;
    public $pvp_tar4 = 0;
	public $pvp_tar = Array();
    public $dto_tar1 = 0;
    public $dto_tar2 = 0;
    public $dto_tar3 = 0;
    public $dto_tar4 = 0;
	public $dto_tar = Array();
    public $fecha_envio = 0;
    public $pendiente_envio = 0;
    public $fecha_creacion_web = 0;
    public $encuadernacion = 0;
    public $edicion = 0;
    public $ano_edicion = 0;
    public $suma_votos = 0;
    public $total_votos = 0;
    public $estado = 0;
    public $stock_disponible = 0;
    public $desde_edad = 0;
    public $hasta_edad = 0;
    public $promociones = 0;
	public $nombrePromociones = '';
	public $descuentoPromociones = 0;
	public $promociones_tarifas_multiples = 0;
    public $nivel_lectura = 0;
    public $curso = 0;
    public $ubicacion1 = 0;
    public $ubicacion2 = 0;
    public $unidades_caja = 1;
    public $tipo_precio = 'F';
    public $nombreColeccion = '';
    public $numeroColeccion = 0;
    public $talla = '';
    public $color = 'gris';
    public $articulo_padre = 0;
	public $objeto_articulo_padre = NULL;
	public $hijos = array();
    public $fecha_ultima_compra = '0000-00-00';
    public $pendiente_envio_suscripcion = 0;
    public $fecha_envio_suscripcion = 0;
    public $temas = array();
    public $lista_escaparates = array();
    //Le añado el descuento para el usuario y el precio para el usuario
    public $descuento_cliente = 0;
    public $pvp_final = 0;
    public $base_final = 0;
	public $pvp_final_sin_dto = 0;	//El precio al que hay que vender el producto SIN el descuento aplicado
	public $base_final_sin_dto = 0;	//La base al que hay que vender el producto SIN el descuento aplicado
	public $adjuntos = array();
	//180807 ==> Cargamos ofertas de artículo:
	public $ofertasRegalo = array();
	//26/Octubre/2018 ==> Añadimos el stock mínimo
	public $stock_minimo = 0;
	//recogemos en estas variables aspectos del constructor para usarlos internamente en la clase
		//Los hago públicos para que estén disponibles en los overrides
	public $cliente = NULL;
	public $cantidad = 1;
	public $linea_lote = NULL;	//Si pertenece a un lote, este es ol objeto del mismo
	//Estas variables son para controlar la carga de los datos
	public $solo_datos = true;
	public $chequeoFamiliar = true;	// ==> Determina si hay que cargar las relaciones padre/hijo
		//14/03/19 Tati=> Añado los datos seo 
	public $nombre_seo = '';
	public $title_seo = '';
	public $descripcion_seo = '';
	public $keywords_seo = '';
		//20/Febrero/2020 ==> IGIC
	public $igic = 0;
		//20/Febrero/2020 ==> Precios de costo:
	public $precio_costo = 0;
	public $precio_costo_dto = 0;
	public $precio_medio_costo = 0;
	public $descuento = 0;
		
	//Vamos a sobreescribir en esta clase los alias y campos porque necesitamos más:
	
	public static function getCampos($soloPrincipal = NULL){
		static::$nombreTabla = strtolower(get_called_class());
		static::getTablaRelacionada();
		//static::$campos_tabla = BaseDatos::$dictionary->{static::$nombreTabla . 'Campos'}; //==> Comento esta línea porque creo que no sirve pa na
		//Una vez que tenemos el nombre de la tabla, vamos a obtener los campos de la misma y los nombres para la selec
		$campos = '';
		if (static::$nombreTabla != ''){
			$campos = ' ';
			if ($soloPrincipal || $soloPrincipal === NULL){
				//$campos .= BaseDatos::dameCamposAlias(BaseDatos::$dictionary->{static::$nombreTabla . 'Campos'}, static::getAlias());
				$campos .= BaseDatos::dameCamposAlias(static::$nombreTabla);
			}
			if ($soloPrincipal === false || $soloPrincipal === NULL){
				/*$campos .= ( (trim($campos) != ' ') ? ', ' : '' ) . 
				BaseDatos::dameCamposAlias(BaseDatos::$dictionary->{TraduccionArticulo::getNombreTabla() . 'Campos'}, TraduccionArticulo::getAlias()) . ', ' .
				BaseDatos::dameCamposAlias(BaseDatos::$dictionary->{SeoArticulo::getNombreTabla() . 'Campos'}, SeoArticulo::getAlias()) . ', ' .
				BaseDatos::dameCamposAlias(BaseDatos::$dictionary->{Familia::getNombreTabla() . 'Campos'}, Familia::getAlias());*/
				$campos .= ( (trim($campos) != ' ') ? ', ' : '' ) . 
				BaseDatos::dameCamposAlias(TraduccionArticulo::getNombreTabla()) . ', ' .
				BaseDatos::dameCamposAlias(SeoArticulo::getNombreTabla()) . ', ' .
				BaseDatos::dameCamposAlias(Familia::getNombreTabla()) . ', ' .
				BaseDatos::dameCamposAlias('promociones');
			}
			if ($soloPrincipal == NULL){
				static::$camposSelect = $campos;
			}
		}
		return($campos);
	}
	
	public static function getNombreTabla($soloPrincipal = NULL){
		$idioma = Idioma::getCurrentLanguaje(true);
		//Incluimos los globals para coger el valor del idioma:
		//include('comunes/globals.php');
		static::$nombreTabla = strtolower(get_called_class());
		static::getTablaRelacionada();
		//Ahora vamos a componer el nombre de la tabla teniendo en cuenta si es sólo principal, si no o si es todo (NULL)
		$consulta = ' ';
		$aliasPropio = static::getAlias();
		//$aliasPropioCodigo = ' `' .  $aliasPropio . '`.`codigo` ';
		if ($soloPrincipal || $soloPrincipal === NULL){
			$consulta .= '`' . static::$nombreTabla . '` as `' .  $aliasPropio . '` ';
		}
		if ($soloPrincipal === false || $soloPrincipal === NULL){	//Si "Sólo principal" es false, consulta sólo me da los leftjoin :D
			//Vamos a hacer los left join necesarios:
			//Ejemplo completo de la llamada:
			//static::getJoin(tabla, Array campos origen (literales empiezan por $), Tabla destino, Array campos origen (literales empiezan por $), array de condiciones, array de operadores, 'left/right join');
			$consulta .= static::getJoin('Articulo', array('codigo', '$' . $idioma), 'TraduccionArticulo', array('articulo', 'idioma'));
			$consulta .= static::getJoin('Articulo', array('codigo', '$' . $idioma), 'SeoArticulo', array('articulo', 'idioma'));
			$consulta .= static::getJoin('Articulo', 'familia', 'Familia', 'codigo');
			$consulta .= static::getJoin('Articulo', 'promociones', 'promociones', 'codigo');
			/*'LEFT JOIN ' . TraduccionArticulo::getNombreTabla() . ' `' . TraduccionArticulo::getAlias() . '` on (' . $aliasPropioCodigo . ' = `' .  TraduccionArticulo::getAlias() . '`.`articulo` AND `' .  TraduccionArticulo::getAlias() . '`.`idioma` = "' . $idioma . '")
			LEFT JOIN ' . SeoArticulo::getNombreTabla() . ' `' . SeoArticulo::getAlias() . '` on(`' . SeoArticulo::getAlias() . '`.`articulo` = ' . $aliasPropioCodigo . ' AND `' . SeoArticulo::getAlias() . '`.`idioma` = "' . $idioma . '" ) 
			LEFT JOIN ' . Familia::getNombreTabla() . ' `' . Familia::getAlias() . '` on (`' . $aliasPropio . '`.`familia` = `' . Familia::getAlias() . '`.`codigo` ) ';*/
		}
		$consulta .= ' ';
		//Sólo asignamos el nombre de la tabla si no nos piden más parámetros
		if ($soloPrincipal == NULL){
			static::$nombreTabla = $consulta;
		}
		//echo($consulta);
		return($consulta);
	}
	
	public static function getWhereTabla(){
		$argumentos = func_get_args();
		$ean_articulo = isset($argumentos[0]) ? $argumentos[0] : NULL;
		$no_web = isset($argumentos[1]) ? $argumentos[1] : 0;
		$limitar = isset($argumentos[2]) ? $argumentos[2] : true;
		
		//include('comunes/globals.php');
		static::$whereSelect = '';
		if ($ean_articulo != NULL) {
			static::$whereSelect .= ' `' . static::getAlias() . '`.`codigo` = "' . $ean_articulo . '" OR `' .  static::getAlias() . '`.`ean` = "' . $ean_articulo . '"';
		}
		if ($no_web) {
			static::$whereSelect .= (static::$whereSelect != '') ? ' AND ' : '';
			static::$whereSelect .= ' `' .  static::getAlias() . '`.`no_web` = 0';
		}
		if (Shop::$configuracion->ocultar_stock_0) {
			static::$whereSelect .= (static::$whereSelect != '') ? ' AND ' : '';
			static::$whereSelect .= ' `' .  static::getAlias() . '`.`stock` > 0';
		}
		if ($limitar){
			static::$whereSelect .= ' LIMIT 1 ';
		}
		return(static::$whereSelect);
	}
	
    function __construct($ean_articulo = NULL, $cliente = '', $cantidad = 1, $linea_lote = 0, $no_web = true, $solo_datos = true) {
        include('comunes/globals.php');
        //Si el cliente que nos han pasado es nulo, cogemos el de la sesión
        if ($cliente == NULL) {
			$this->cliente = Usuario::logueado();
			//Pedro 01/Septiembre/2020
			//Si el cliente no tiene código, asignamos el cliente cotado (para el cálculo de precios)
			if ( (! is_a($this->cliente, 'Usuario')) || ( (is_a($this->cliente, 'Usuario')) && ($this->cliente->codigo == '') ) ){
				$this->cliente = new Usuario(Shop::$configuracion->cliente_contado_web);
			}
		}
        $idioma = Idioma::getCurrentLanguaje(true);
        $cod_articulo = NULL;
		$filaArticulo = NULL;
		$this->cantidad = $cantidad;
		$this->linea_lote = (is_object($linea_lote)) ? $linea_lote : NULL;	//Por retrocompatibilidad dejo esto así para que si me mandan un número no haga nada
		//Vamos a convertir este constructor en un V2:
		if (is_a($ean_articulo, 'OpcionesWidget')) {
			$opciones = $ean_articulo;
			$ean_articulo = ($opciones->configuracion->ean_articulo != NULL) ? $opciones->configuracion->ean_articulo : 0;
			//Pedro 01/Septiembre/2020 ==> No podemos comprobar si nos han pasado un cliente numérico, los códigos son alfabéticos.
			$cliente = ($opciones->configuracion->cliente != '') ? $opciones->configuracion->cliente : $this->cliente;
			if (!is_a($cliente, 'Usuario')){
				$cliente = ($cliente != '') ? $cliente : Shop::$configuracion->cliente_contado_web;
				$cliente = new Usuario($cliente);
			}
			$this->cliente = $cliente;
			$this->cantidad = ($opciones->configuracion->cantidad != NULL) ? $opciones->configuracion->cantidad : $cantidad;
			$this->linea_lote = ($opciones->configuracion->linea_lote != NULL) ? $opciones->configuracion->linea_lote : $linea_lote;
			$no_web = ($opciones->configuracion->no_web != NULL) ? $opciones->configuracion->no_web : $no_web;
			$this->solo_datos = ($opciones->configuracion->solo_datos != NULL) ? $opciones->configuracion->solo_datos : $this->solo_datos;
			$this->chequeoFamiliar = ($opciones->configuracion->chequeoFamiliar != NULL) ? $opciones->configuracion->chequeoFamiliar : $this->chequeoFamiliar;
			$filaArticulo = ($opciones->configuracion->filaArticulo != NULL) ? $opciones->configuracion->filaArticulo : $filaArticulo;
		}
		
        //Si el ean recibido es un array, entonces hemos recibido ean y cóo
        if (is_array($ean_articulo)) {
            if (count($ean_articulo) > 1) {
                $ean_articulo = $ean_articulo[1];
            }
            $ean_articulo = $ean_articulo[0];
        }
		
		//Ojo a la posibilidad de haber recibido una "fila" de artículo:
		$fila = NULL;
		
		if ($filaArticulo == NULL){
			if (intval($ean_articulo) > 0) {
				//Preparamos el FROM con las uniones correspondientes
				$sentencia_sql = 'SELECT ' . Articulo::getCampos() . ' 
									FROM ' . Articulo::getNombreTabla() . '
									WHERE ' .Articulo::getWhereTabla($ean_articulo, $no_web);
				
				//echo("$sentencia_sql <br />\n");

				$bd = new BaseDatos();
				if ($bd->isConectado()){
					$bd->setConsultaSQL($sentencia_sql);
					$fila = $bd->getFila();
				}
			}
		}else{
			$fila = $filaArticulo;
		}
		
		$this->extractData($fila);
	}

	public function extractData($fila){
		$idioma = Idioma::getCurrentLanguaje(true);
		if ($fila != NULL){
			$aliasTabla = static::getAlias();
			$this->codigo = $this->getProp($fila, 'codigo');
			$this->tipo = $this->getProp($fila, 'tipo');
			//Pedro 16/Octubre/2019 ==> Todos los datos SEO se inicializan al nombre del producto
			$this->nombre_seo = $this->title_seo = $this->keywords_seo = $this->descripcion_seo = $this->nombre = trim($this->getProp($fila, 'nombre'));
			$this->subtitulo = $this->getProp($fila, 'subtitulo');
			$this->stock = (int) $this->getProp($fila, 'stock');
			$this->pvp = (float) $this->getProp($fila, 'pvp');
			$this->iva = (float) $this->getProp($fila, 'iva');
			$this->igic = (float) $this->getProp($fila, 'igic');
			$this->base = Price::getBase($this->pvp, $this->iva);
			$this->precio_costo = (float) $this->getProp($fila, 'precio_costo');
			$this->precio_costo_dto = (float) $this->getProp($fila, 'precio_costo_dto');
			$this->precio_medio_costo = (float) $this->getProp($fila, 'precio_medio_costo');
			$this->descuento = (float) $this->getProp($fila, 'descuento');
			$this->ean = trim($this->getProp($fila, 'ean'));
			$this->referencia = trim($this->getProp($fila, 'referencia'));
			$this->isbn = trim($this->getProp($fila, 'isbn'));
			$this->autor = $this->getProp($fila, 'autor');
			$this->fecha_alta = $this->getProp($fila, 'fecha_alta');
			$this->num_paginas = (int) $this->getProp($fila, 'num_paginas');
			$this->peso = (int) $this->getProp($fila, 'peso');
			$this->alto = (int) $this->getProp($fila, 'alto');
			$this->ancho = (int) $this->getProp($fila, 'ancho');
			$this->ilustrador = $this->getProp($fila, 'ilustrador');
			$this->fecha_ult_modif = $this->getProp($fila, 'fecha_ult_modif');
			$this->editorial = $this->getProp($fila, 'editorial');
			$this->cod_editorial = $this->getProp($fila, 'cod_editorial');
			$this->cod_distribuidor = $this->getProp($fila, 'cod_distribuidor');
			$this->coleccion = $this->getProp($fila, 'coleccion');
			$this->no_web = (int) $this->getProp($fila, 'no_web');
			$this->familia = $this->getProp($fila, 'familia');
			//$this->asigna_familia(); ==> TODO
			$this->familia_nombre = $this->getProp($fila, 'nombre', Familia::getAlias());
			$this->grupo_familia = $this->getProp($fila, 'grupo', Familia::getAlias());			
			$this->foto = (int) $this->getProp($fila, 'foto');
			$this->tema = $this->getProp($fila, 'tema');
			$this->pvpoferta = (float) $this->getProp($fila, 'pvpoferta');
			if ($this->pvpoferta == 0) {
				$this->pvpoferta = $this->pvp;
			}
			$this->dto_maximo = (int) $this->getProp($fila, 'dto_maximo');
			$this->texto = (int) $this->getProp($fila, 'texto');
			$this->pvp_tar1 = (float) $this->getProp($fila, 'pvp_tar1');
			$this->pvp_tar2 = (float) $this->getProp($fila, 'pvp_tar2');
			$this->pvp_tar3 = (float) $this->getProp($fila, 'pvp_tar3');
			$this->pvp_tar4 = (float) $this->getProp($fila, 'pvp_tar4');
			$this->pvp_tar = [$this->pvp_tar1, $this->pvp_tar2, $this->pvp_tar3, $this->pvp_tar4];
			$this->dto_tar1 = (int) $this->getProp($fila, 'dto_tar1');
			$this->dto_tar2 = (int) $this->getProp($fila, 'dto_tar2');
			$this->dto_tar3 = (int) $this->getProp($fila, 'dto_tar3');
			$this->dto_tar4 = (int) $this->getProp($fila, 'dto_tar4');
			$this->dto_tar = [$this->dto_tar1, $this->dto_tar2, $this->dto_tar3, $this->dto_tar4];
			$this->fecha_envio = $this->getProp($fila, 'fecha_envio');
			$this->pendiente_envio = $this->getProp($fila, 'pendiente_envio');
			$this->fecha_creacion_web = $this->getProp($fila, 'fecha_creacion_web');
			$this->encuadernacion = $this->getProp($fila, 'encuadernacion');
			$this->edicion = (int) $this->getProp($fila, 'edicion');
			$this->ano_edicion = (int) $this->getProp($fila, 'ano_edicion');
			$this->suma_votos = (int) $this->getProp($fila, 'suma_votos');
			$this->total_votos = (int) $this->getProp($fila, 'total_votos');
			$this->estado = (int) $this->getProp($fila, 'estado');
			$this->stock_disponible = (int) $this->getProp($fila, 'stock_disponible');
			$this->desde_edad = (int) $this->getProp($fila, 'desde_edad');
			$this->hasta_edad = (int) ($this->getProp($fila, 'hasta_edad') == 0) ? 99 : $this->getProp($fila, 'hasta_edad');
			//Aquí cargo la tabla promociones, teniendo en cuenta que lo que voy a hacer es traerme al producto el nombre de la misma y el dto:
			$this->promociones = (int) $this->getProp($fila, 'promociones');
			$this->nombrePromociones = (int) $this->getProp($fila, 'nombre', BaseDatos::dameAlias('promociones'));
			$this->descuentoPromociones = (int) $this->getProp($fila, 'descuento', BaseDatos::dameAlias('promociones'));
			$this->promociones_tarifas_multiples = (int) $this->getProp($fila, 'tarifas_multiples', BaseDatos::dameAlias('promociones'));
			//Ojo, es posible que la promoción esté fuera de fecha, es por ello que vamos a asegurarnos de que no sea así.
			$fecha_inicio_promocion = strtotime($this->getProp($fila, 'desde_fecha', BaseDatos::dameAlias('promociones')));
			$fecha_fin_promocion = strtotime($this->getProp($fila, 'hasta_fecha', BaseDatos::dameAlias('promociones')));
			$hoy = time();
			if ( ($hoy < $fecha_inicio_promocion) || ($hoy > $fecha_fin_promocion) ){
				$this->promociones = 0;
				$this->nombrePromociones = '';
				$this->descuentoPromociones = 0;
				$this->promociones_tarifas_multiples = 0;
			}
			//Sigo leyendo datos del producto
			$this->nivel_lectura = (int) $this->getProp($fila, 'nivel_lectura');
			$this->curso = $this->getProp($fila, 'curso');
			$this->ubicacion1 = $this->getProp($fila, 'ubicacion1');
			$this->ubicacion2 = $this->getProp($fila, 'ubicacion2');
			$this->unidades_caja = $this->getProp($fila, 'unidades_caja');
			//Pequeña correción, puede que unidades caja sea 0
			$this->unidades_caja = ($this->unidades_caja == 0) ? 1 : $this->unidades_caja;
			//OJO, siempre que sean libros, las unidades x caja será 1 (se hace así desde que descubrimos que galo usa este campo para otra cosa en libros
			$this->unidades_caja = ($this->tipo == 'L') ? 1 : $this->unidades_caja;
			$this->tipo_precio = ($this->getProp($fila, 'tipo_precio') == '') ? $this->tipo_precio : $this->getProp($fila, 'tipo_precio');
			$this->nombreColeccion = $this->getProp($fila, 'nombre_coleccion');
			$this->numeroColeccion = $this->getProp($fila, 'numero_coleccion');
			$this->talla = $this->getProp($fila, 'talla');
			$this->color = $this->getProp($fila, 'color');
			$this->articulo_padre = $this->getProp($fila, 'articulo_padre');
			
			$this->fecha_ultima_compra = $this->getProp($fila, 'fecha_ultima_compra');
			$this->pendiente_envio_suscripcion = (int) $this->getProp($fila, 'pendiente_envio_suscripcion');
			$this->fecha_envio_suscripcion = $this->getProp($fila, 'fecha_envio_suscripcion');
			//Traducciones
			$this->observaciones = $this->getProp($fila, 'traduccion', TraduccionArticulo::getAlias());
			//Las observaciones a veces vienen con doble barra, primero quitamos los intros y después el resto:
			//$this->observaciones = str_replace('\"', '&#34;', $this->observaciones);
			$this->observaciones = str_replace('\n', '<br>', $this->observaciones);
			$this->observaciones = stripslashes($this->observaciones);
			//echo $this->observaciones;
			//Pedro 16/Octubre/2019 ==> Si hay traducciones, las pasamos a la descripción:
			if ($this->observaciones != ''){
				$this->descripcion_seo = substr($this->observaciones, 0, 160);	//Extraemos sólo los primeros 160 caracteres
			}
			//datos SEO:
				//Pedro 16/Octubre/2019 ==> Vamos a componer los datos SEO de otra manera a partir de ahora:
				//					---------------------------------
				//					|	URL	|	Title	|	Usuario	|
				//					---------------------------------
				//	Nombre natural	|	V	|	  V		|	  D		|
				//					---------------------------------
				//	Nombre SEO		|	D	|	  V		|	  X		|
				//					---------------------------------
				//	Title Seo		|	X	|	  D		|	  X		|
				//					---------------------------------
				//	X => No se usa
				//	V => se utiliza si no hay valor por defecto
				//	D => Es el valor que debe coger por defecto, independientemente del resto de valores
			//Vamos a obtener los datos en variables:
			$nombre_seo = $this->getProp($fila, 'nombre', SeoArticulo::getAlias());
			$title_seo = $this->getProp($fila, 'title', SeoArticulo::getAlias());
			$keywords_seo = $this->getProp($fila, 'keywords', SeoArticulo::getAlias());
			$descripcion_seo = $this->getProp($fila, 'descripcion', SeoArticulo::getAlias());
			//Ahora mismo TODOS los campos SEO se han igualado al nombre excepto la descripción:
			$this->nombre_seo = ($nombre_seo != '') ? $nombre_seo : $this->nombre_seo;	//Con esto el nombre SEO es él mismo si tiene valor o el nombre del producto
			$this->title_seo = ($title_seo != '') ? $title_seo : $this->nombre_seo;	//Con esto el Title SEO es él mismo si tiene valor o el nombre_seo
			$this->keywords_seo = ($keywords_seo != '') ? $keywords_seo : $this->title_seo;	//Con esto los Keywords son elos mismos si tienen valor o el title_seo
			$this->descripcion_seo = ($descripcion_seo != '') ? $descripcion_seo : $this->descripcion_seo;	//En este caso se usa el valor asignado antes si no tiene nada	

			//Añadido el 26/Octubre/2018
			$this->stock_minimo = $this->getProp($fila, 'stock_minimo');
			//Si el artículo no pertenece a ningún escaparate, vamos a crear el 'otros-productos'
			$this->url = Shop::$configuracion->url . traducir('otros-productos');

			//Sólo cargamos el resto de datos si así se nos ha especificado
			if (!$this->solo_datos) {
				//$this->asigna_temas();
				$this->rellena_escaparates();
				//Como tenemos todos los escaparates del producto, vamos a coger el primero para la URL (si es q hay alguno)
				if (count($this->lista_escaparates) > 0) {
					//Si pertenece a algúne scaparate, cogemos SIEMPRE el primero
					$this->url = $this->lista_escaparates[0]->url;
				}
			}else{
				//Esto es antiguo pero lo mantenemos por ahora
				//Vamos a cargar aquí mismo el último escaparate:
				$sentencia_sql = 'SELECT IFNULL(`b`.`nombre`, `c`.`nombre`) nombre_escaparate
								FROM `categorias_productos` a, (`traducesca` b LEFT JOIN `cesca_seo` c ON `b`.`escaparate` = `c`.`cescaparate` AND `b`.`idioma` = "' . $idioma . '" AND `c`.`idioma` = "' . $idioma . '") 
								WHERE `a`.`articulo` = ' . $this->codigo . '  
								AND `a`.`categoria` = `b`.`escaparate`
								ORDER BY `orden` DESC LIMIT 0,1';
				//echo("$sentencia_sql\n<br />");
				$bdUrl = new BaseDatos();
				$bdUrl->setConsultaSQL($sentencia_sql);
				if ($fila = $bdUrl->getFila()){
					$this->url = Shop::$configuracion->url . SEO::URL($fila['nombre_escaparate']);
				}
			}

			//Por último, dejamos la URL con un formato bonito		
			$this->url .= '/' . SEO::URL($this->nombre_seo) . '-p' . $this->ean;
			//Si el producto NO está en un lote, entonces cargamos su precio de forma natural
			$this->pvp_final = 0;
			//Necesitamos asegurarnos de que el lote que nos han pasado contiene el artículo
			if ($this->linea_lote != NULL) {
				if ( ($this->linea_lote->trabaja_cantidades) || ($this->linea_lote->trabaja_cantidades_pvp) ){
					$this->cantidad = $this->linea_lote->cantidad;	//El lote lleva una cantidad fija, es la que se meterá en la cesta
					if ($this->linea_lote->trabaja_cantidades_pvp){
						//TODO, aquí hay que trabajar el código de descuento aplicado
						$this->pvpoferta = $this->linea_lote->pvp;
						$this->pvp_final = $this->linea_lote->pvp;
						$this->pvp_final_sin_dto = $this->linea_lote->pvp;
					}
				}
			}

			//Si no tenemos PVP, vamos a ver el precio del artículo y su tarifa, etc...
			if ($this->pvp_final == 0) {
				//Lo primero es controlar que no haya un descuento global:
				if (Shop::$configuracion->descuentoGlobal > 0){
					$pvp_dto_arti = array(Shop::$configuracion->descuentoGlobal, $this->pvp);
				}else{
					//Vamos a calcular precio y descuento
					$pvp_dto_arti = $this->calcula_precio_articulo($this->cliente, $this->cantidad);
				}
/*
				//Pedro 11/Febrero/2020 ==> Los descuentos por promociones se aplicarán en la función de cálculo de precio del artículo
				$this->descuento_cliente = ($this->descuentoPromociones > 0 ) ? $this->descuentoPromociones  : $pvp_dto_arti[0];	//Las promociones van SIEMPRE aplicadas, por tanti si las hay, se suman
				$pvp_dto_arti[0] = $this->descuento_cliente;	//Es posible que se haya aplicado alguna promocion, así que hay que actualizar el descuento
				if ($pvp_dto_arti[1] == 0) {
					$pvp_dto_arti[1] = $this->pvp;
				}
*/
				$this->pvp_final_sin_dto = $pvp_dto_arti[1];
				$this->descuento_cliente = $pvp_dto_arti[0];
				$this->pvp_final = Price::setDiscount($this->pvp_final_sin_dto, $this->descuento_cliente);
			} else {
				
			}
			
			/*
			//Pedro 10/Julio/2019 ==> Esto tenemos que hacerlo más arriba
			//Si hemos recibido alg??ote, es el momento de ver si tenemos ese lote en los descuentos para ver cual es su descuento
			if ($this->lote > 0) {
				$indice_dto_lote = Lote::buscar_dto_lote($this->lote);
				$cod_dto_lote_actual = '';
				$porcen_dto_actual = 0;
				if ($indice_dto_lote > -1) {
					$array_descuentos_lotes = Sesion::get('array_descuentos_lotes');
					$cod_dto_lote_actual = explode('|', $array_descuentos_lotes[$indice_dto_lote]);
					$porcen_dto_actual = $cod_dto_lote_actual[1];
					$this->pvp_final_sin_dto = $this->pvp_final;
					$this->pvp_final = Price::setDiscount($this->pvp_final, $porcen_dto_actual);
				}
			}*/
			
			//Vamos a cargar los temas del producto:
			$this->temas = Tema::cargarDesdeArticulo($this->codigo);
			$this->tematica_restrictiva = $this->getTematicaRestrictiva();	//Pedro 09/Septiembre/2019 ==> Cargamos la temática más restrictiva para este artículo
		}
		//Lo ultimo es calcular la base del pvp final:
		$this->base_final = Price::getBase($this->pvp_final, ( (($this->igic > 0) && (Shop::$configuracion->igic_trabaja)) ? $this->igic : $this->iva));
		$this->base_final_sin_dto = Price::getBase($this->pvp_final_sin_dto, ( (($this->igic > 0) && (Shop::$configuracion->igic_trabaja)) ? $this->igic : $this->iva));
		$this->base_pvpoferta = Price::getBase($this->pvpoferta, ( (($this->igic > 0) && (Shop::$configuracion->igic_trabaja)) ? $this->igic : $this->iva));
		$this->adjuntos = Ebook::cargarAdjuntos($this->ean);
		//Pedro 16/Julio/2020 ==> Es el momento de cargar los datos del padre, sólo para los que estén vacíos:
		if ($this->objeto_articulo_padre != NULL){
			$this->cargarDatosPadre();
		}
		//Pedro 16/Julio/2020 ==> Vamos a ver si hay que cargar las relaciones familares
		if ($this->chequeoFamiliar){
			$tieneHijos = $this->hasHijos();
			if ($this->articulo_padre > 0){
				//Un artículo Padre NO puede tener a su vez otro padre, así evitamos que pueda haber reduncancia:
				if (!$tieneHijos){
					//Vamos a cargar el artículo:
					//$this->objeto_articulo_padre = new Articulo(new OpcionesWidget(array('ean_articulo' => $this->articulo_padre, 'chequeoFamiliar' => false)));
				}
			//Si no tiene padre, puede que tenga hijos
			}else if($tieneHijos){
				$this->cargarHijos();
			}
		}
	}
	
	function venderAdjuntos($cod_usuario){
		include('comunes/globals.php');
		$retorno = false;
		//Controlamos si hemos recibido un código o un objeto
		$usuario = NULL;
		if (is_a($cod_usuario, 'Usuario')){
			$usuario = $cod_usuario;
			$cod_usuario = $usuario->codigo;
		}else{
			$usuario = new Usuario($cod_usuario);
			$cod_usuario = $usuario->codigo;
		}
		//si tenemos un usuario bien creado vamos a utilizarlo:
		if ($cod_usuario != ''){
			$bd = new BaseDatos();

			//Vamos a limpiar las descargas que ya  existan para ese cliente y ean:
			$sentenciaBorrado = 'DELETE FROM `descargas_ebook` WHERE `ean` = ' . $this->ean . ' AND `usuario` = \'' . $cod_usuario . '\';';
			$bd->setConsultaSQL($sentenciaBorrado);
			
			//Necesitamos los adjuntos:
			$adjuntos = Ebook::getRutasAdjuntos($this->ean);
			$sentencia_sql = '';
			foreach($adjuntos as $clave => $valor){
				$sentencia_sql .= ( ($sentencia_sql != '')?',':'' ) . ' ( \'' . $this->ean . '\', \'' . $valor . '\', \'' . $cod_usuario . '\' ) ';
			}
			//echo("$sentencia_sql<br />\n");
			
			//Una vez q tenemos la select, vamos a hacer el insert
			if ($sentencia_sql != ''){
				$sentencia_sql = 'INSERT INTO descargas_ebook (`ean`, `ruta`, `usuario`) VALUES ' . $sentencia_sql;
			}
			//Para hacer pruebas, no actualizo el pedido
			$bd->setConsultaSQL($sentencia_sql);
			if ($bd->getNumeroFilas() > 0){
				$retorno = true;
			}
		}
		return($retorno);
	}
	
    function __destruct() {
        //Limpiamos los hijos que tenga asociados al artículo
        for ($i = 0; $i < count($this->temas); $i++) {
            unset($this->temas[$i]);
        }
        for ($i = 0; $i < count($this->lista_escaparates); $i++) {
            unset($this->lista_escaparates[$i]);
        }
    }
	
    public function rellena_escaparates() {
        include('comunes/globals.php');
		$idioma = Idioma::getCurrentLanguaje(true);
        $sentencia_sql = 'SELECT `categoria` FROM `categorias_productos` WHERE `articulo` = ' . $this->codigo . ' ORDER BY `orden` DESC';
        //echo("$sentencia_sql\n<br />");
		$bd = new BaseDatos();
		$bd->setConsultaSQL($sentencia_sql);
		while ($fila = $bd->getFila()){
                    //comento esta linea porque antes la select era por codigo y ahora en la tabla nueva que hemos creado es categoria
			//$escaparateTMP = new Escaparate($fila['codigo'], 1);
			$escaparateTMP = new Escaparate($fila['categoria'], 1);
			if ($escaparateTMP->objeto_vacio == 0) {
				$this->lista_escaparates[count($this->lista_escaparates)] = $escaparateTMP;
			}
		}
    }

    public function dame_indice_escaparate_codigo($codigo_a_buscar) {
        $retorno = NULL;
        //Buscamos el índice en el array de códigos de escaparate
        $encontrado = false;
        for ($i = 0; ( ($i < count($this->lista_escaparates)) && (!($encontrado))); $i++) {
            if ($this->lista_escaparates[$i]->codigo == $codigo_a_buscar) {
                $retorno = $i;
                $encontrado = true;
            }
        }
        return($retorno);
    }

    public function productos_relacionados($cantidad = 0, $seleccion_x_escaparate = false) {
        include('comunes/globals.php');
        $retorno = 0;
        if ($cantidad == 0) {
            $cantidad = Shop::$configuracion->elementos_relacionados;
        }
        $codigos_a_quitar = "'" . $this->codigo . "'";
		/*
        if ($seleccion_x_escaparate) {
            //Cuando hay selección por escaparate, cargamos primero los asociados por escaparate y después por otros datos:
            $this->lista_articulos = $this->relacionados_x_escaparate($cantidad, $this->lista_articulos, $codigos_a_quitar);
            $codigos_a_quitar = $this->extraerCodigo(false, $this->codigo);
            $this->lista_articulos = $this->relacionados_x_datosArti($cantidad, $this->lista_articulos, $codigos_a_quitar);
        } else {
            $this->lista_articulos = $this->relacionados_x_datosArti($cantidad, $this->lista_articulos, $codigos_a_quitar);
            $codigos_a_quitar = $this->extraerCodigo(false, $this->codigo);
            $this->lista_articulos = $this->relacionados_x_escaparate($cantidad, $this->lista_articulos, $codigos_a_quitar);
        }
		*/
		$this->relacionados_x_temas($cantidad, $this->lista_articulos, $codigos_a_quitar);
		$this->relacionados_x_escaparate($cantidad, $this->lista_articulos, $codigos_a_quitar);
		$this->relacionados_x_datosArti($cantidad, $this->lista_articulos, $codigos_a_quitar);
        $retorno = count($this->lista_articulos);
		//var_dump($this->lista_articulos);
        return($retorno);
    }

	public function relacionados_x_temas($cantidad, $lista_actual = array(), $codigos_a_quitar = "") {
        include('comunes/globals.php');
		//Sentencia por optimizar
        if (count($lista_actual) < $cantidad) {
			//Vamos a coger los filtrados:
			$this->adaptarFiltrado('', true);	//==> Encargado de generar los filtrados de sesión o temporales del usuario
			$this->filtradoGlobal();			//==> Encargado de generar los filtrados globales de la web
            $cantidad = $cantidad - count($lista_actual);
			//Modificado por Pedro el 17/Junio/2019 ==> Si no hay cantidad no seguimos
			if ( ($cantidad > 0) && ($this->tematica_restrictiva != '') ){
				//Vamos a componernos una select en condiciones:
				$this->nombreTablas = static::getNombreTabla() . ' 
						LEFT JOIN `temasarti` ON 
							( `temasarti`.`articulo` = `' . $this->getAlias() . '`.`codigo` ) ';
				//Pedro 16/Octubre/2019 ==> Sacamos el count para contar los productos, estas selects pueden ser gigantescas
				$this->countCamposTabla = ' COUNT(DISTINCT(`' . Articulo::getAlias() . '`.`codigo`)) total '; 
				$this->camposTabla = ' DISTINCT ' . static::getCampos();	//Le dejo el distinct para que saque los que tienen distinto código
				//Componemos los where asegurándonos de que son los temas del artículo y sólo los artículos con la temática restrictiva
				$this->whereTabla =  '( `' . $this->getAlias() . '`.`tema` = \'' . $this->tematica_restrictiva . '\' 
								OR `temasarti`.`tema` = \'' . $this->tematica_restrictiva . '\' )  
								AND ' . '`' . static::getAlias() . '`.no_web = 0 ';

				//Creamos el orden:
				$this->crea_orden(' ORDER BY RAND() ', true);

				//Cargamos los productos
				$this->carga_articulos(0, $cantidad);
				/*echo("<!--\n");
				echo( 'SELECT ' . $this->camposTabla . ' 
				FROM ' . $this->nombreTablas . '
				WHERE ' . $this->whereTabla);
				echo("-->\n");*/
			}
        }
        return($this->lista_articulos);
    }

    public function relacionados_x_datosArti($cantidad, $lista_actual = array(), $codigos_a_quitar = "") {
        include('comunes/globals.php');
		//Sentencia por optimizar
        if (count($lista_actual) < $cantidad) {
			//Vamos a coger los filtrados:
			$this->adaptarFiltrado('', true);	//==> Encargado de generar los filtrados de sesión o temporales del usuario
			$this->filtradoGlobal();			//==> Encargado de generar los filtrados globales de la web
            $cantidad = $cantidad - count($lista_actual);
			//Modificado por Pedro el 17/Junio/2019 ==> Si no hay cantidad no seguimos
			if ($cantidad > 0){
				//Vamos a componernos una select en condiciones:
				$this->nombreTablas = static::getNombreTabla();
				//Pedro 16/Octubre/2019 ==> Sacamos el count para contar los productos, estas selects pueden ser gigantescas
				$this->countCamposTabla = ' COUNT(DISTINCT(`' . Articulo::getAlias() . '`.`codigo`)) total '; 
				$this->camposTabla = ' DISTINCT ' . static::getCampos();	//Le dejo el distinct para que saque los que tienen distinto código
				//Pedro 27/06/2019 ==> SI el artículo no tiene ni editorial ni distribuidor, no asociamos nada
				if (($this->editorial != '') || ($this->cod_distribuidor > 0) ){
					//Componemos los where con los campos de editorial y alias
					$this->whereTabla = ($this->editorial != '') ? ('`' . static::getAlias() . '`.editorial = \'' . $this->editorial . '\' ') : '';
					$this->whereTabla .= ( ( ($this->whereTabla != '') && ($this->cod_distribuidor > 0) ) ? ' OR ' : '')
						.( ($this->cod_distribuidor > 0) ? ('`' . static::getAlias() . '`.cod_distribuidor = \'' . $this->cod_distribuidor . '\' ') : '');
					//Añadimos el "no web"
					$this->whereTabla = ( ($this->whereTabla != '') ? (' ( ' . $this->whereTabla . ' ) AND ') : '' )
						. '`' . static::getAlias() . '`.no_web = 0 ';
					//Creamos el orden:
					$this->crea_orden(' ORDER BY RAND() ', true);

					//Cargamos los productos
					$this->carga_articulos(0, $cantidad);
				}
			}
        }
        return($this->lista_articulos);
    }

	public function relacionados_x_autor($cantidad, $lista_actual = array(), $codigos_a_quitar = "") {
        include('comunes/globals.php');
		//Sentencia por optimizar
        if (count($lista_actual) < $cantidad) {
			//Vamos a coger los filtrados:
			$this->adaptarFiltrado('', true);	//==> Encargado de generar los filtrados de sesión o temporales del usuario
			$this->filtradoGlobal();			//==> Encargado de generar los filtrados globales de la web
            $cantidad = $cantidad - count($lista_actual);
			//Modificado por Pedro el 17/Junio/2019 ==> Si no hay cantidad no seguimos
			if ($cantidad > 0){
				//Vamos a componernos una select en condiciones:
				$this->nombreTablas = static::getNombreTabla();
				//Pedro 16/Octubre/2019 ==> Sacamos el count para contar los productos, estas selects pueden ser gigantescas
				$this->countCamposTabla = ' COUNT(DISTINCT(`' . Articulo::getAlias() . '`.`codigo`)) total '; 
				$this->camposTabla = ' DISTINCT ' . static::getCampos();	//Le dejo el distinct para que saque los que tienen distinto código
				//Pedro 27/06/2019 ==> SI el artículo no tiene ni autor ni distribuidor, no asociamos nada
				if ($this->autor != ''){
					//Componemos los where con los campos de editorial y alias
					$this->whereTabla = ($this->autor != '') ? ('`' . static::getAlias() . '`.autor = \'' . $this->autor . '\' ') : '';
					//Añadimos el "no web"
					$this->whereTabla = ( ($this->whereTabla != '') ? (' ( ' . $this->whereTabla . ' ) AND ') : '' )
						. '`' . static::getAlias() . '`.no_web = 0 ';
					//Creamos el orden:
					$this->crea_orden(' ORDER BY RAND() ', true);

					//Cargamos los productos
					$this->carga_articulos(0, $cantidad);
				}
			}
        }
        return($this->lista_articulos);
    }

    public function relacionados_x_escaparate($cantidad, $lista_actual = array(), $codigos_a_quitar = '') {
        //En esta función vamos a cargar 10 veces más productos de los que indica "cantidad", después cortaremos la lista para sacar 3 de forma aleatoria
        include('comunes/globals.php');
        if (count($lista_actual) < $cantidad) {
			//Vamos a coger el filtrado global:
			$this->filtradoGlobal();
            $cantidad = $cantidad - count($lista_actual);
            if ($cantidad > 0) {				
                //Vamos a coger los filtrados:
				$this->adaptarFiltrado('', true);	//==> Encargado de generar los filtrados de sesión o temporales del usuario
				$this->filtradoGlobal();			//==> Encargado de generar los filtrados globales de la web
				$cantidad = $cantidad - count($lista_actual);
				//Vamos a componernos una select en condiciones:
				$this->nombreTablas = ' `categorias_productos` `a` LEFT JOIN `categorias_productos` `b`  '
											. ' ON ( `a`.`orden` < 10000 AND `b`.`orden` < 10000 AND `a`.`categoria` = `b`.`categoria`) '	//Hemos añadido el orden para que sean del mismo escaparate (Pedro 09/Septiembre/2019)
											. ' LEFT JOIN `' . static::getTablaRelacionada('articulo') . '` as `' . static::getAlias() . '` '
											. ' ON (`a`.`articulo` = `' . static::getAlias() . '`.`codigo` ) '
										. static::getNombreTabla(false);
				//Pedro 16/Octubre/2019 ==> Sacamos el count para contar los productos, estas selects pueden ser gigantescas
				$this->countCamposTabla = ' COUNT(DISTINCT(`' . Articulo::getAlias() . '`.`codigo`)) total '; 
				$this->camposTabla = ' DISTINCT `a`.`articulo`, ' . static::getCampos();
				//Añadimos el "no web"
				$this->whereTabla = '`b`.`articulo` = ' . $this->codigo . ' AND `' . static::getAlias() . '`.no_web = 0 ';
					//. ( ($this->filtrado_global != '') ? ' AND ' . $this->filtrado_global . ' ' : '');
				//Creamos el orden:
				$this->crea_orden(' ORDER BY RAND() ', true);
				//Cargamos los artículo
				$this->carga_articulos(0, $cantidad);
			}
        }
        return($lista_actual);
    }

    public function temas_con_traduccion() {
        return(array_filter($this->temas, 'Articulo::filtrar_temas_con_traduccion'));
    }

    public static function filtrar_temas_con_tracuccion($objeto_tema) {
        if ($objeto_tema->traduccion != '') {
            return(true);
        } else {
            return(false);
        }
    }

	//Pedro 16/Julio/2020
	//Esta función pasa ser un alias de una que hemos mejorado
    public static function dame_valor_campo($campo, $codigoArticulo) {
		return(static::dameCampo($codigoArticulo, $campo));
        /*include 'comunes/globals.php';
        $valor = null;
        $sentencia_sql = "SELECT $campo FROM articulo  WHERE codigo = $codigoArticulo";
        //echo("$sentencia_sql<br />\n");
        if ($resultado = mysqli_query($conexionBD, $sentencia_sql)) {
            if ($fila = mysqli_fetch_array($resultado)) {
                $valor = $fila[$campo];
            }
        }
        return $valor;*/
    }

    public function getJSON() {
        $prop = get_object_vars($this);
        $resp = '{ ';
        foreach ($prop as $key => $value) {
            if (gettype($value) == 'string') {
                $resp .= '"' . $key . '":' . json_encode(htmlspecialchars_decode($value)) . ',';
            } else {
                $resp .= '"' . $key . '":' . json_encode($value) . ',';
            }
        }
        $resp = substr($resp, 0, -1) . "}";
        return $resp;
    }

    public function hasHijos() {
        //modificada por Tomás: vamos a aligerar este proceso 
        $total = 0;
		$codigo = intval($this->codigo);
		if ($codigo > 0){
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$sentencia = 'SELECT codigo FROM articulo  WHERE articulo_padre = ' . $this->codigo . ' LIMIT 1';
				$bd->setConsultaSQL($sentencia);
				$total = $bd->getNumeroFilas();
			}
		}
		return($total);
    }

	public function cargarHijos() {
        //modificada por Tomás: vamos a aligerar este proceso 
        $total = 0;
		$codigo = intval($this->codigo);
		if ($codigo > 0){
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$sentencia = 'SELECT codigo FROM articulo  WHERE articulo_padre = \'' . $codigo . '\'';
				//echo($sentencia);
				$bd->setConsultaSQL($sentencia);
				while($fila = $bd->getFila()){
					$this->hijos[] = new Articulo(new OpcionesWidget(array('ean_articulo' => $fila['codigo'], 'chequeoFamiliar' => false)));
					$total++;
				}
			}
		}
		return($total);
    }

	//Pedro 16/Julio/2020 ==> Mejoramos la carga de artículo haciendo sólo una select que nos dará el valor correcto
    public static function buscaArticulo($codigo, $nombreCampo = 'codigo') {
		$retorno = array();
		$nombreCampo = (is_array($nombreCampo)) ? $nombreCampo : array($nombreCampo);
        $listaCampos = implode(',', $nombreCampo);
		
        if ($conexionBD) {
			//Vamos a hacer una SELECT que nos de lo que necesitamos, la limitamos a 1 
			$sentencia = 'SELECT ' . $listaCampos . ', IF(ean = \'' . $codigo . '\', 0, 1) orden 
							FROM articulo 
							WHERE ean = \'' . $codigo . '\' OR codigo = \'' . $codigo . '\' 
							ORDER BY orden ASC  LIMIT 1;';
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$bd->setConsultaSQL($sentencia);
				if($fila = $bd->getFila()){
					foreach($nombreCampo as $key => $campo){
						$retorno[$campo] = $fila[$campo];
					}
				}
			}
        }
		//si sólo nos han pedido un campo, lo devolvemos directamente sin array:
		if (count($retorno) == 1){
			$retorno = $retorno[0];
		}
        return($retorno);
    }

    public static function dameCampo($codigo, $nombreCampo = array()) {
        include('comunes/globals.php');
        $retorno = 0;
		//Si no nos pasan nombre de campo no hacemos nada:
		$nombreCampo = (is_array($nombreCampo)) ? $nombreCampo : array($nombreCampo);
		
        $codigo = $this::buscaArticulo($codigo);
        if ($conexionBD) {
            $sentencia_sql = "SELECT $nombreCampo FROM articulo WHERE codigo = $codigo";
            if ($resultado = mysqli_query($conexionBD, $sentencia_sql)) {
                if ($fila = mysqli_fetch_array($resultado)) {
                    $retorno = $fila[$nombreCampo];
                }
            }
        }
        return($retorno);
    }

	//180807 ==> pedro, cargar ofertas articulo
	public function cargarOfertas(){
		$this->ofertasRegalo = OfertasRegalo::cargarOfertas($this->codigo);
	}
	
	public static function editorialesTodas($filtro = ''){
		$retorno = array();
		$bd = new BaseDatos();
		if ($bd->isConectado()){
			$filtro = ($filtro != '') ? ' WHERE ' . $filtro : '';
			$sentencia = 'SELECT DISTINCT `editorial` FROM `articulo` ' . $filtro . ' GROUP BY `editorial` ORDER BY `editorial`;';
			$bd->setConsultaSQL($sentencia);
			while($fila = $bd->getFila()){
				if ($fila['editorial'] != ''){
					$retorno[] = $fila['editorial'];
				}
			}
		}
		return($retorno);
	}


	private function getTematicaRestrictiva(){
		//Vamos a cargar la temática más restrictiva para este artículo:
		$return = $this->tema;
		foreach($this->temas as $key => $tema){
			$return = (strlen($return) > strlen($tema->codigo)) ? $return : $tema->codigo;
		}
		return($return);
	}
	
	public function setSEO(){
		SEO::setName($this->nombre_seo);
		SEO::setTitle($this->title_seo);
		SEO::setKeywords($this->keywords_seo);
		SEO::setDescription($this->descripcion_seo);
	}

	//Funciones de precios:
	private function calcula_precio_articulo($cliente = NULL, $cantidad = 1) {
		//include('comunes/globals.php');
		//Pedro 10/Febrero/2020 ==> A partir de ahora se calcula PRIMERO PVP y SEGUNDO DESCUENTO siguiendo el orden que tiene en SINLIB/HERBOLIB
		if ($cliente == NULL) {
			$cliente = $this->cliente;
		}
		$precio_final = 0;
		$dto = 0;
		$pvp_arti = 0;
		$retorno = array(0, 0);

		$precio_final = ($this->pvpoferta != $this->pvp) ? $this->pvpoferta : 0;	//16/Enero/2019 ==> El precio de oferta es, por defecto igual al PVP y claro, más abajo comprobamos que sea 0
		$pvp = $this->pvp;
		
		if ( (Shop::$configuracion->trabaja_descuentos) && ($precio_final == 0)){	//Si ya se ha puesto un precio de oferta no se tienen en cuenta los descuentos
			//Si no tenemos precio_final, vamos a ver el descuento del cliente por código promocional
			if ($precio_final == 0) {
				//EMPEZAMOS POR EL PRECIO:
				switch (Shop::$configuracion->programa_arminet) {
					case 1:
						//Sindis
						//$precio_final = $this->dame_precio_articulo_sindis($this->codigo, $cantidad, $cliente);
						$precio_final = $this->dame_precio_articulo_sindis($cantidad);
						break;
					case 2:
						//Herbolib, por ahora igual que en sinlib
						$precio_final = $this->dame_precio_articulo_herbolib($cantidad);
						break;
					case 0:
					default:
						//Por defecto sinlib
						$precio_final = $this->dame_precio_articulo_sinlib($cantidad);
						break;
				}
				//Ahora vamos con el DESCUENTO SI PROCEDE
				/*echo("<!--");
				var_dump($precio_final);
				var_dump(Shop::$empresa->herbolib_modulo_distribucion);
				var_dump(Shop::$configuracion->programa_arminet);
				var_dump(Shop::$empresa->forzar_descuentos);
				echo("Calculamos el descuento si procede\n");
				echo("-->");*/
				//Pedro 23/07/2020 ==> EL precio final puede que no sea 0, si no que sea el PVP del artículo
				if ( ( ($precio_final == 0) || ($precio_final == $pvp) ) || 
					(Shop::$empresa->herbolib_modulo_distribucion && Shop::$configuracion->programa_arminet == 2) ||
					(Shop::$empresa->forzar_descuentos) ){
					/*echo("<!--");
					echo("Procede\n");
					echo("-->");*/
					//Si es sindis, o sinlib, hay que hacer una cosa u otra
					switch (Shop::$configuracion->programa_arminet) {
						case 1:
							//Sindis
							$dto = $this->dame_descuento_articulo_sindis($cantidad, $this->codigo, $cliente);
							break;
						case 2:
							//Herbolib
							//Por defecto sinlib
							$dto = $this->dame_descuento_articulo_herbolib($cantidad, $cliente);
							break;
						case 0:
						default:
							//Sinlib
							//Por defecto sinlib
							$dto = $this->dame_descuento_articulo_sinlib($cantidad, $cliente);
							break;
							break;
					}
					//Ahora tenemos en cuenta el descuento máximo:
					$dto = min($dto, $this->dto_maximo);
				}
			}

			//TODO
			//Si ni por esas tenemos precio, entonces vamos a ver si hubiese algún descuento especial para ese cliente
			/*if (($dto == 0) && ($precio_final == $pvp )) {
				$dto = dame_descuento($this->codigo, $cliente);
			}*/
		}

		//Pedro 15/Mayo/2020 ==> Si e preco es 0 le asignamos el PVP:
		if ($precio_final == 0){
			$precio_final = $pvp;
		}
		$retorno[0] = $dto;
		$retorno[1] = $precio_final;
		return($retorno);
	}
	//--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
	// Devolvemos el precio de un artículo para un cliente
	//--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
	private function dame_precio_articulo_sindis($cantidad = 1, $cliente = NULL, $prensa = 0){
		return($this->dame_precio_articulo($cantidad, $cliente, $prensa));
	}
	private function dame_precio_articulo_herbolib($cantidad = 1, $cliente = NULL, $prensa = 0){
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}else{
			if (is_numeric($cliente)){
				$cliente = new Usuario($cliente);
			}else if (!is_a($cliente, 'Usuario')){
				$cliente = new Usuario(0);	
			}
		}
		$pvp = 0;
		if (is_a($cliente, 'Usuario')){
			//19/Febrero/2020 ==> Empezamos por los precios de costo (costo, costo medio y costo +dto)
			if ( ($cliente->vender_costo) || ($cliente->vender_precio_medio_costo) || ($cliente->vender_precio_costo_con_descuento)){
				if ($this->tipo_precio == 'L'){
					if (Shop::$configuracion->igic_trabaja){
						$iva = $this->igic;
					}else{
						$iva = $this->iva;
					}
					if ($cliente->vender_costo){
						$pvp = $this->precio_costo * (1 + ($iva / 100) );
					}else if ($cliente->vender_precio_costo_con_descuento){
						$pvp = $this->precio_costo_dto * (1 + ($iva / 100) );
					}else if ($cliente->vender_precio_medio_costo){
						if ($this->precio_medio_costo == 0){
							$pvp = $this->precio_costo_dto * (1 + ($iva / 100) );
						}else{
							$pvp = $this->precio_medio_costo * (1 + ($iva / 100) );
						}
					}
				}else{
					$pvp = $this->pvp;
				}
			}else{
				//__________________________________________________________________________________________________________________________________________
				//_____________________________________________________ ARTIOFERTAS ________________________________________________________________________
				//__________________________________________________________________________________________________________________________________________
				if ($pvp == 0) {
					$pvp = $this->calcula_precio_oferta_arti();
				}
				//__________________________________________________________________________________________________________________________________________
				//_____________________________________________________ DTOS_CLI_ART _______________________________________________________________________
				//__________________________________________________________________________________________________________________________________________
				if ($pvp == 0) {
					$pvp = $this->calcula_precio_cliente($cliente);
				}
				//__________________________________________________________________________________________________________________________________________
				//_____________________________________________________ PRECIOS ESCALADOS __________________________________________________________________
				//__________________________________________________________________________________________________________________________________________
				if (($pvp == 0) && ( $cliente->precios_escalados == 1 )) {
					$pvp = $this->dame_precio_escalado($cantidad);
				}
				//__________________________________________________________________________________________________________________________________________
				//_______________________________________________________________ TARIFAS X FAMILIA ________________________________________________________
				//__________________________________________________________________________________________________________________________________________
				if (($pvp == 0) && ($this->tipo == "P")) {	//Este código de aquí hacia abajo sólo afacta si el articulo es P
					if (!Shop::$configuracion->tarifas_multiples){
						//Si no tiene tarifas el cliente cogemos el PVP
						if ($cliente->tarifa == 0){
							$pvp = $this->pvp;
						}else if ($cliente->tarifa > 0){
							$nombreCampo = 'pvp_tar' . $cliente->tarifa;
							$pvp = $this->{$nombreCampo};
						}
					}else{
						//Precio tarifa por familia
						if ($pvp == 0){
							$pvp = $this->calcula_precio_tarifa_x_familia($cliente);
						}
						if ($pvp == 0){	//Si el PVP sigue siendo 0, vamos a ver si hay tarifas múltples
							//__________________________________________________________________________________________________________________________________________
							//_______________________________________________________________ TARIFAS MULTIPLES ________________________________________________________
							//__________________________________________________________________________________________________________________________________________
							$pvp = $this->calcula_precio_tarifa_multiple($cliente);
						}
					}
				}
				//No hay PVP, lo cogemos de la ficha del artículo
				if ($pvp == 0){
					$pvp = $this->pvp;
				}
				//Si restamos el iva, vamos a hacerlo:
				if ($this->cliente->resta_iva) {
					$pvp = Price::getBase($pvp, $iva);
				}
			}
			
		}
		return($pvp);
	}
	private function dame_precio_articulo_sinlib($cantidad = 1, $cliente = NULL, $prensa = 0){
		return($this->dame_precio_articulo($cantidad, $cliente, $prensa));
	}
	private function dame_precio_articulo($cantidad = 1, $cliente = NULL, $prensa = 0){
		//En Herbolib aparece esto:
			//if ('pClientePreciosCompra' | 'pClientePreciosCompraMedio' | 'pClientePreciosCompraDTO').....
			//Esto no lo hacemos aquí porque es para vender a precio de costo
		//El cliente que recibimos es el de la web. Necesitamos el de sinlib
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}else{
			if (is_numeric($cliente)){
				$cliente = new Usuario($cliente);
			}else if (!is_a($cliente, 'Usuario')){
				$cliente = new Usuario(Shop::$configuracion->cliente_contado_web);
			}
		}
		
		$pvp = 0;
		//A partir de ahora necesitamos el código SINLIB del cliente que será el que se use en los cálculos:
		if (is_a($cliente, 'Usuario')){
			//Ahora con los datos que tenemos vamos a ir viendo que precio tiene el producto
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ LÍNEAS DE PROMOCIÓN ________________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($pvp == 0) {
				//echo('Descuento de promoción');
				$pvp = $this->calcula_precio_lineas_promocion();
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ ARTIOFERTAS ________________________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($pvp == 0) {
				$pvp = $this->calcula_precio_oferta_arti();
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DTOS_CLI_ART _______________________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($pvp == 0) {
				$pvp = $this->calcula_precio_cliente($cliente);
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ PRECIOS ESCALADOS __________________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if (($pvp == 0) && ( $cliente->precios_escalados == 1 )) {
				$pvp = $this->dame_precio_escalado($cantidad);
			}
			//__________________________________________________________________________________________________________________________________________
			//_______________________________________________________________ TARIFAS X FAMILIA ________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if (($pvp == 0) && ($this->tipo == "P")) {	//Este código de aquí hacia abajo sólo afacta si el articulo es P
				//echo("<!-- Artículo tipo 'p' -->");
				//Vamos a ver las precios especiales por tafia (los cuatro precios fijos de la ficha del artículo:
				if ($cliente->tarifa > 0){
					$nombreCampo = 'pvp_tar' . $cliente->tarifa;
					$pvp = $this->{$nombreCampo};
					//echo("<!-- PVP: {$pvp} -->");
				}
				//echo("<!-- PVP: {$pvp} -->");
				if ($pvp == 0){
					$pvp = $this->calcula_precio_tarifa_x_familia($cliente);
				}
				if ($pvp == 0){	//Si el PVP sigue siendo 0, vamos a ver si hay tarifas múltples
					//__________________________________________________________________________________________________________________________________________
					//_______________________________________________________________ TARIFAS MULTIPLES ________________________________________________________
					//__________________________________________________________________________________________________________________________________________
					$pvp = $this->calcula_precio_tarifa_multiple($cliente);
				}
			}
			//si no hay precio, cogemos el del artículo
			if ($pvp == 0) {
				$pvp = $this->pvp;
			}
			//Ahora vamos a ver si hay que restar el iva
			if ($this->cliente->resta_iva) {
				$pvp = calcula_base($pvp, $iva);
			}
		}
		return($pvp);
	}
	//------------------------------------------------------------------------------------------------------------------------------
	// Devolvemos el descuento del producto
	//------------------------------------------------------------------------------------------------------------------------------
	private function dame_descuento_articulo_sindis($cantidad = 1, $cliente = NULL, $prensa = 0){
		return($this->dame_descuento_articulo($cantidad, $cliente, $prensa));
	}
	private function dame_descuento_articulo_herbolib($cantidad = 1, $cliente = NULL, $prensa = 0){
		/*echo("<!--");
		echo("Cargamos los descuentos\n");
		echo("-->");*/
		//El cliente que recibimos es el de la web. Necesitamos el de sinlib
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}else{
			if (is_numeric($cliente)){
				$cliente = new Usuario($cliente);
			}else if (!is_a($cliente, 'Usuario')){
				$cliente = new Usuario(0);	
			}
		}
		$descuento = 0;
		//A partir de ahora necesitamos el código SINLIB del cliente que será el que se use en los cálculos:
		if (is_a($cliente, 'Usuario')){
			/*echo("<!--");
			echo("Es un usuario dentro de la función principal\n");
			echo("-->");*/
			//
			if ( ($cliente->vender_costo) || ($cliente->vender_precio_medio_costo) || ($cliente->vender_precio_costo_con_descuento)){
				$descuento = $this->descuento;
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DESCUENTOS ESCALADOS _______________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if (($descuento == 0) && ( $cliente->precios_escalados == 1 )) {
				$descuento = $this->dame_descuento_escalado($cantidad);
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DESCUENTOS POR PROMOCION ___________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($descuento == 0){
				$descuento = $this->dame_descuento_promocion($cliente);
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DESCUENTOS TEXTO, DÍA DEL LIBRO, DÍA PAPELERÍA _____________________________________
			//__________________________________________________________________________________________________________________________________________
			$mes_actual = (int)date('m');
			if ( ($descuento == 0) && ($this->tipo == 'L') && 
				($this->texto) && ($mes_actual >= Shop::$configuracion->mes_inicio_texto) && ($mes_actual <= Shop::$configuracion->mes_fin_texto)){
				$descuento = Shop::$configuracion->dto_texto;
			}
			if ( ($descuento == 0) && ($this->tipo == 'L') && (Shop::$configuracion->dto_dia_libro > 0)){
				$descuento = Shop::$configuracion->dto_dia_libro;
			}
			if ( ($descuento == 0) && ($this->tipo == 'P') && (Shop::$configuracion->dto_papeleria > 0)){
				$descuento = Shop::$configuracion->dto_papeleria;
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DESCUENTOS ARTICULO Y CLIENTE  _____________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($descuento == 0){
				$descuento = $this->dto_articulo_cliente($cliente);
			}
			if ($descuento == 0){
				$descuento = $this->dame_descuento_tarifa_x_familia($cliente);
			}
			//__________________________________________________________________________________________________________________________________________
			//______________________________________________ DESCUENTOS GRUPO FAMILIA __________________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($descuento == 0){
				$descuento = $this->dto_grupo_familia($cliente);
			}
			//__________________________________________________________________________________________________________________________________________
			//______________________________________________ DESCUENTOS GENERALES DEL CLIENTE __________________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($descuento == 0){
				if ($this->tipo == 'L'){
					if ($this->texto){
						$descuento = $cliente->descuento_texto;
					}else{
						$descuento = $cliente->dto_dia_libro;
					}
				}else{
					$descuento = $cliente->descuento_papeleria;
					if (!Shop::$configuracion->tarifas_multiples){
						//Si no tiene tarifas el cliente cogemos el descuento
						if ($cliente->tarifa > 0){
							$nombreCampo = 'dto_tar' . $cliente->tarifa;
							$descuento = $this->{$nombreCampo};
						}
					}else{
						//Vamos a cargar el descuento de tarifas múltiples
						if ( ($cliente->tarifas_multiples > 0) && ($cliente->tarifas_multiples != 255) ){
							$descuento = descuento_tari_arti($cliente); 
						}
						if ($descuento == 0){
							$descuento = $cliente->descuento_papeleria;
						}
					}
				}
			}
		}
		return($descuento);
	}
	private function dame_descuento_articulo_sinlib($cantidad = 1, $cliente = NULL, $prensa = 0){
		return($this->dame_descuento_articulo($cantidad, $cliente, $prensa));
	}
	private function dame_descuento_articulo($cantidad = 1, $cliente = NULL, $prensa = 0) {
		//El cliente que recibimos es el de la web. Necesitamos el de sinlib
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}else{
			if (is_numeric($cliente)){
				$cliente = new Usuario($cliente);
			}else if (!is_a($cliente, 'Usuario')){
				$cliente = new Usuario(0);	
			}
		}
		$descuento = 0;
		//A partir de ahora necesitamos el código SINLIB del cliente que será el que se use en los cálculos:
		if (is_a($cliente, 'Usuario')){
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DESCUENTOS ESCALADOS _______________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if (($descuento == 0) && ( $cliente->precios_escalados == 1 )) {
				$descuento = $this->dame_descuento_escalado($cantidad);
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DESCUENTOS POR PROMOCION ___________________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($descuento == 0){
				$descuento = $this->dame_descuento_promocion($cliente);
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DESCUENTOS TEXTO, DÍA DEL LIBRO, DÍA PAPELERÍA _____________________________________
			//__________________________________________________________________________________________________________________________________________
			$mes_actual = (int)date('m');
			if ( ($descuento == 0) && ($this->tipo == 'L') && 
				($this->texto) && ($mes_actual >= Shop::$configuracion->mes_inicio_texto) && ($mes_actual <= Shop::$configuracion->mes_fin_texto)){
				$descuento = Shop::$configuracion->dto_texto;
			}
			if ( ($descuento == 0) && ($this->tipo == 'L') && (Shop::$configuracion->dto_dia_libro > 0)){
				$descuento = Shop::$configuracion->dto_dia_libro;
			}
			if ( ($descuento == 0) && ($this->tipo == 'P') && (Shop::$configuracion->descuento_papeleria > 0)){
				$descuento = Shop::$configuracion->descuento_papeleria;
			}
			//__________________________________________________________________________________________________________________________________________
			//_____________________________________________________ DESCUENTOS ARTICULO Y CLIENTE  _____________________________________________________
			//__________________________________________________________________________________________________________________________________________
			if ($descuento == 0){
				$descuento = $this->dto_articulo_cliente($cliente);
			}
			
			
			
		}
		return($descuento);
	}
	
/*	
	//25/Noviembre/2019 Métodos mágicos que voy a utilizar para cuando se serializa/desserializa esto
	public function __sleep(){
		return(array(
		'codigo', 'tipo', 'nombre', 'subtitulo', 'stock', 'pvp', 'iva', 'base', 'ean', 'referencia', 'isbn', 'autor', 'fecha_alta', 'num_paginas', 'peso', 
		'alto', 'ancho', 'ilustrador', 'observaciones', 'fecha_ult_modif', 'editorial', 'cod_editorial', 'cod_distribuidor', 'coleccion', 'no_web', 'familia', 
		'familia_nombre', 'foto', 'tema', 'tematica_restrictiva', 'pvpoferta', 'base_pvpoferta', 'dto_maximo', 'texto', 'pvp_tar1', 'pvp_tar2', 'pvp_tar3', 
		'pvp_tar4', 'dto_tar1', 'dto_tar2', 'dto_tar3', 'dto_tar4', 'fecha_envio', 'pendiente_envio', 'fecha_creacion_web', 'encuadernacion', 'edicion', 
		'ano_edicion', 'suma_votos', 'total_votos', 'estado', 'stock_disponible', 'desde_edad', 'hasta_edad', 'promociones', 'nombrePromociones', 'descuentoPromociones', 
		'nivel_lectura', 'curso', 'ubicacion1', 'ubicacion2', 'unidades_caja', 'tipo_precio', 'nombreColeccion', 'numeroColeccion', 'talla', 'color', 
		'articulo_padre', 'fecha_ultima_compra', 'pendiente_envio_suscripcion', 'fecha_envio_suscripcion', 'descuento_cliente', 'pvp_final', 'base_final', 
		'pvp_final_sin_dto', 'base_final_sin_dto', 'stock_minimo', 'cantidad', 'solo_datos', 'nombre_seo', 'title_seo', 'descripcion_seo', 'keywords_seo'
		));
	}
	public function __wakeup (){
		//TODO ==> hay que cargar el objeto tipo de envío así como el array de lotes asociados
	}
*/
	//Pedro 10/Febrero/2020 ==> Vamos a incluir en el artículo las funciones de precios y descuentos (en el futuro es posible que las saquemos
	function calcula_precio_oferta_arti() {
		$hoy = date('Y-m-d');
		$retorno = 0;
		//El artículo es lo primero que tenemos que usar en esta función para los índices
		$sentencia_sql = 'SELECT pvp FROM
							`artiofertas` 
						WHERE articulo = \'' . $this->codigo . '\' AND  desde_fecha <=  \'' . $hoy . '\' AND hasta_fecha >=  \'' . $hoy . '\'
						LIMIT 1;';
		//echo($sentencia_sql);
		$bd = new BaseDatos();
        if ($bd->isConectado()){
			$bd->setConsultaSQL($sentencia_sql);
			 if ($fila = $bd->getFila()){
				$retorno = $fila['pvp'];
			 }
		}
		return($retorno);
	}

	function calcula_precio_lineas_promocion($tarifaMultiple = NULL) {
		$tarifaMultiple = ($tarifaMultiple == NULL) ? $this->cliente->tarifas_multiples : $tarifaMultiple;
		$hoy = date('Y-m-d');
		$retorno = 0;
		//El artículo es lo primero que tenemos que usar en esta función para los índices
		$sentencia_sql = 'SELECT `lin_promocion`.`pvp` FROM
							`lin_promocion`, `promociones`
						WHERE `lin_promocion`.`articulo` = \'' . $this->codigo . '\' 
							AND `lin_promocion`.`promocion` = `promociones`.`codigo` AND `promociones`.`tarifas_multiples` = \'' . $tarifaMultiple . '\'
							AND  `promociones`.`desde_fecha` <=  \'' . $hoy . '\' AND `promociones`.`hasta_fecha` >=  \'' . $hoy . '\'
						LIMIT 1;';
		//echo($sentencia_sql);
		$bd = new BaseDatos();
        if ($bd->isConectado()){
			$bd->setConsultaSQL($sentencia_sql);
			 if ($fila = $bd->getFila()){
				$retorno = $fila['pvp'];
			 }
		}
		return($retorno);
	}


	function calcula_precio_cliente($cliente = NULL) {
		$retorno = 0;
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}
		if (is_a($cliente, 'Usuario')){
			$sentencia_sql = 'SELECT pvp FROM `dtos_cli_art` WHERE articulo = \''  . $this->codigo . '\' AND cliente = \'' . $cliente->codigo_sinlib . '\';
							LIMIT 1;';
			//echo($sentencia_sql);
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$bd->setConsultaSQL($sentencia_sql);
				if ($fila = $bd->getFila()){
					$retorno = $fila['pvp'];
				}
			}
		}
		return($retorno);
	}
	
	function dame_precio_escalado($cantidad = 1) {
		$retorno = 0;
		$hoy = date('Y-m-d');
		$sentencia_sql = 'SELECT pvp FROM preciosescal WHERE 
							articulo = \'' . $this->codigo . '\' AND 
							' . $cantidad  . ' >= desde AND ' . $cantidad . ' <= hasta 
							AND \'' . $hoy . '\' >= desde_fecha AND \'' . $hoy . '\' <= hasta_fecha
							LIMIT 1;';
		//echo("$sentencia_sql<br />\n");
		$bd = new BaseDatos();
		if ($bd->isConectado()){
			$bd->setConsultaSQL($sentencia_sql);
			if ($fila = $bd->getFila()){
				$retorno = $fila['pvp'];
			}
		}
		return($retorno);
	}

	function calcula_precio_tarifa_x_familia($cliente){
		$retorno = 0;
		if (is_a($cliente, 'Usuario')){
			//Si no usa tarifas múltiples, cogemos la tarifa del artículo
			if (($cliente->tarifas_multiples == 0) || ($cliente->tarifas_multiples == 255)) {
				//Como usa tarifas múltiples, vamos a consultarlas
				$sentencia_sql = 'SELECT `tariarti`.`pvp` `pvp` FROM `dtosclifam`, `tariarti`
							WHERE `dtosclifam`.`cliente` = \'' . $cliente->codigo_sinlib . '\' AND `dtosclifam`.`familia` = \'' . $this->familia . '\'
							AND `tariarti`.`tarifa` = `dtosclifam`.`tarifa` AND `tariarti`.`articulo` = \'' . $this->codigo . '\'
							AND `tariarti`.`descuento` = \'0\'
							LIMIT 1;';
				//echo("Tarifa x familia:<br />$sentencia_sql<br />\n");
				$bd = new BaseDatos();
				if ($bd->isConectado()){
					$bd->setConsultaSQL($sentencia_sql);
					if ($fila = $bd->getFila()){
						$retorno = $fila['pvp'];
					}
				}
			}
		}
	}
	
	function calcula_precio_tarifa_multiple($cliente = NULL, $tarifa = NULL){
		$retorno = 0;
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}
		//Modificado por pedro para tener en cuenta que una tarifa puede tener padres
		if (is_a($cliente, 'Usuario')){
			$tarifa = ($tarifa == NULL) ? $this->cliente->tarifas_multiples : $tarifa;
			$sentencia_sql = 'SELECT `pvp`, `descuento` FROM tariarti 
								WHERE articulo = \'' . $this->codigo . '\' AND tarifa = \'' . $tarifa . '\' 
									AND \'' . $tarifa . '\' != \'255\' 
								LIMIT 1; ';
			//echo("Datos articulo:<br />$sentencia_sql<br />\n");
			$encontradaTarifa = false;
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$bd->setConsultaSQL($sentencia_sql);
				if ($fila = $bd->getFila()){
					if ($fila['descuento'] == 0){
						$retorno = $fila['pvp'];
					}
					$encontradaTarifa = true;
				}
			}
			if (!$encontradaTarifa){
				//vamos a ver si hay una tarifa padre
				$sentencia_sql = 'SELECT `tarifa_padre` FROM tarifas 
								WHERE codigo = \'' . $tarifa . '\' 
								LIMIT 1; ';
				if ($bd->isConectado()){
					$bd->setConsultaSQL($sentencia_sql);
					if ($fila = $bd->getFila()){
						$tarifa_padre = $fila['tarifa_padre'];
						if ( ($tarifa_padre > 0) && ($tarifa_padre != 255) ){
							$retorno = $this->calcula_precio_tarifa_multiple($cliente, $tarifa_padre);
						}
						$encontradaTarifa = true;
					}
				}
			}
			return($retorno);
		}
	}
	
	//Funciones de descuento:
	function dame_descuento_escalado($cantidad = 1) {
		$retorno = 0;
		$hoy = date('Y-m-d');
		$sentencia_sql = 'SELECT `descuento` FROM `preciosescal` WHERE 
							`articulo` = \'' . $this->codigo . '\' AND 
							' . $cantidad  . ' >= `desde` AND ' . $cantidad . ' <= `hasta `
							AND \'' . $hoy . '\' >= `desde_fecha` AND \'' . $hoy . '\' <= `hasta_fecha`
							LIMIT 1;';
		//echo("$sentencia_sql<br />\n");
		$bd = new BaseDatos();
		if ($bd->isConectado()){
			$bd->setConsultaSQL($sentencia_sql);
			if ($fila = $bd->getFila()){
				$retorno = $fila['descuento'];
			}
		}
		return($retorno);
	}
	
	function dame_descuento_promocion($cliente = NULL){
		$retorno = 0;
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}
		/*echo("<!--");
		echo("Inicio\n");
		echo("-->");*/
		if (is_a($cliente, 'Usuario')){
			/*echo("<!--");
			echo("Es un usuario\n");
			echo("-->");*/
			if ( (Shop::$configuracion->tarifas_multiples) && ($this->promociones_tarifas_multiples > 0) ){
				if ($this->promociones_tarifas_multiples == $cliente->tarifas_multiples){
					$retorno = $this->descuentoPromociones;
				}
				/*echo("<!--");
				echo("tafifa múltiple\n");
				echo("-->");*/
			}else{
				/*echo("<!--");
				echo("Descuento promocional\n");
				echo("{$this->descuentoPromociones}\n");
				echo("-->");*/
				$retorno = $this->descuentoPromociones;
			}
		}
		return($retorno);
	}
	
	function dto_articulo_cliente($cliente = NULL) {
		$retorno = 0;
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}
		if (is_a($cliente, 'Usuario')){
			$sentencia_sql = 'SELECT `descuento` FROM `dtos_cli_art` WHERE 
				`articulo` = \'' . $this->codigo . '\' AND `cliente` = \'' . $cliente->codigo_sinlib . '\'
				LIMIT 1;';
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$bd->setConsultaSQL($sentencia_sql);
				if ($fila = $bd->getFila()){
					$retorno = $fila['descuento'];
				}
			}
		}
		return($retorno);
	}
	
	function dame_descuento_tarifa_x_familia($cliente = NULL){
		$retorno = 0;
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}
		if (is_a($cliente, 'Usuario')){
			$sentencia_sql = 'SELECT `descuento`, `tarifa` FROM `dtosclifam` WHERE `cliente` = \'' . $cliente->codigo_sinlib . '\' 
								AND `familia` = \'' . $this->familia . '\'
								LIMIT 1; ';
			//echo("$sentencia_sql<br />\n");
			$tarifa = 0;
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$bd->setConsultaSQL($sentencia_sql);
				if ($fila = $bd->getFila()){
					$retorno = $fila['descuento'];
					$tarifa = $fila['tarifa'];
				}
				if ( (Shop::$configuracion->tarifas_multiples) && ($tarifa > 0) ){
					//Si se usan tarifas múltiples, hay que cargar el descuento del padre
					$sentencia_sql = 'SELECT `descuento` FROM `tarifas` WHERE `codigo` = \'' . $tarifa . '\' 
								LIMIT 1; ';
								$bd->setConsultaSQL($sentencia_sql);
					if ($fila = $bd->getFila()){
						$retorno = $fila['descuento'];
					}
				}
			}
		}
		return($retorno);
	}

	function dto_grupo_familia($cliente = NULL) {
		$retorno = 0;
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}
		if (is_a($cliente, 'Usuario')){
			$sentencia_sql = 'SELECT `descuento` FROM `dtogrupofamilia` 
								WHERE `tarifadtopape` = \'' . $cliente->tarifa . '\'
								AND `grupofamilia` = \'' . $this->grupo_familia . '\'
								LIMIT 1;';
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$bd->setConsultaSQL($sentencia_sql);
				if ($fila = $bd->getFila()){
					$retorno = $fila['descuento'];
				}
			}
		}
		return($retorno);
	}

	function descuento_tari_arti($cliente = NULL){
		$retorno = 0;
		if ($cliente == NULL){
			$cliente = $this->cliente;
		}
		//Modificado por pedro para tener en cuenta que una tarifa puede tener padres
		if (is_a($cliente, 'Usuario')){
			$tarifa = $this->cliente->tarifas_multiples;
			$sentencia_sql = 'SELECT `descuento` FROM tariarti 
								WHERE articulo = \'' . $this->codigo . '\' AND tarifa = \'' . $tarifa . '\' 
								LIMIT 1; ';
			//echo("Datos articulo:<br />$sentencia_sql<br />\n");
			$bd = new BaseDatos();
			if ($bd->isConectado()){
				$bd->setConsultaSQL($sentencia_sql);
				if ($fila = $bd->getFila()){
					if ($fila['descuento'] == 0){
						$retorno = $fila['pvp'];
					}
				}
			}
			return($retorno);
		}
	}

	//vamos a recorrer todos los campos del objeto y, si NO están en la lista de "bloqueados" los cogemos del padre si están vacíos:
	public function cargarDatosPadre(){
		$camposBloqueados = array('codigo', 'tipo', 'fecha_alta', 'fecha_ult_modif'. 'stock', 'no_web', 'suma_votos', 'total_votos', 'estado', 'fecha_ultima_compra',
		'pvp', 'iva', 'igic', 'base', 'precio_costo', 'precio_costo_dto', 'precio_medio_costo', 'descuento', 'pvpoferta', 'dto_maximo', 'pvp_tar1', 'pvp_tar2',
		'pvp_tar3', 'dto_tar4', 'dto_tar', 'promociones', 'descuentoPromociones', 'promociones_tarifas_multiples',  'base_final', 'base_final_sin_dto', 'base_pvpoferta');
		$campos = get_object_vars($this);
		foreach($campos as $key => $campo){
			if (!in_array($campo, $camposBloqueados)){
				$this->$campo = ($this->$campo == '' || $this->$campo == '0' || $this->$campo == NULL) ? $this->objeto_articulo_padre->$campo : $this->$campo;
			}
		}
		//Si el precio final del producto es 0, entonces, hay que coger TODOS estos datos del padre, si no, manda el artículo
		if ($this->pvp == 0){
			$this->pvp = (float) $this->objeto_articulo_padre->pvp;
			$this->iva = (float) $this->objeto_articulo_padre->iva;
			$this->igic = (float) $this->objeto_articulo_padre->igic;
			$this->base = $this->objeto_articulo_padre->base;
			$this->precio_costo = (float) $this->objeto_articulo_padre->precio_costo;
			$this->precio_costo_dto = (float) $this->objeto_articulo_padre->precio_costo_dto;
			$this->precio_medio_costo = (float) $this->objeto_articulo_padre->precio_medio_costo;
			$this->descuento = (float) $this->objeto_articulo_padre->descuento;
			$this->pvpoferta = (float) $this->objeto_articulo_padre->pvpoferta;
			$this->dto_maximo = (int) $this->objeto_articulo_padre->dto_maximo;
			$this->pvp_tar1 = (float) $this->objeto_articulo_padre->pvp_tar1;
			$this->pvp_tar2 = (float) $this->objeto_articulo_padre->pvp_tar2;
			$this->pvp_tar3 = (float) $this->objeto_articulo_padre->pvp_tar3;
			$this->pvp_tar4 = (float) $this->objeto_articulo_padre->pvp_tar4;
			$this->pvp_tar = [$this->pvp_tar1, $this->pvp_tar2, $this->pvp_tar3, $this->pvp_tar4];
			$this->dto_tar1 = (int) $this->objeto_articulo_padre->dto_tar1;
			$this->dto_tar2 = (int) $this->objeto_articulo_padre->dto_tar2;
			$this->dto_tar3 = (int) $this->objeto_articulo_padre->dto_tar3;
			$this->dto_tar4 = (int) $this->objeto_articulo_padre->dto_tar4;
			$this->dto_tar = [$this->dto_tar1, $this->dto_tar2, $this->dto_tar3, $this->dto_tar4];
			//Aquí cargo la tabla promociones, teniendo en cuenta que lo que voy a hacer es traerme al producto el nombre de la misma y el dto:
			$this->promociones = (int) $this->objeto_articulo_padre->promociones;
			$this->nombrePromociones = (int) $this->objeto_articulo_padre->nombrePromociones;
			$this->descuentoPromociones = (int) $this->objeto_articulo_padre->descuentoPromociones;
			$this->promociones_tarifas_multiples = (int) $this->objeto_articulo_padre->promociones_tarifas_multiples;
			//Lo ultimo es calcular la base del pvp final:
			$this->base_final = $this->objeto_articulo_padre->base_final;
			$this->base_final_sin_dto = $this->objeto_articulo_padre->base_final_sin_dto;
			$this->base_pvpoferta = $this->objeto_articulo_padre->base_pvpoferta;
		}
	}

	//Marina(23/06/2020) creo una nueva funcion para obtener una cadena identificativa del producto
	function __toString(){
		return ($this->codigo . ';' . $this->ean . ';' . $this->nombre);
	}
}
