<?php
namespace hakoniwa\blocks\ssr\rss;

use hakoniwa\blocks\init\Define;

/**
 * ブロック登録
 */
class Register {

	/**
	 * 初期設定
	 */
	public function __construct() {
		// 
		add_action( 'init', array( $this, 'register_block' ) );
	}

	/**
	 * ブロック登録
	 *
	 * @return void
	 */
	public function register_block() {

		$args = array(
			'numberOfItems'   => array(
				'type'    => 'number',
				'default' => 4,
			),
			'columns'     => array(
				'type'    => 'number',
				'default' => 2,
			),
			'layout'        => array(
				'type'    => 'string',
				'default' => 'grid',
			),
			'listLayoutType'  => array(
				'type'    => 'string',
				'default' => '',
			),
			'listBorderStyle' => array(
				'type'    => 'string',
				'default' => 'none',
			),
			'defaultImage'         => array(
				'type'    => 'string',
				'default' => '',
			),
			'displayThumbnail'   => array(
				'type'    => 'boolean',
				'default' => true,
			),
			'displayAuthor'        => array(
				'type'    => 'boolean',
				'default' => true,
			),
			'displayDate'          => array(
				'type'    => 'boolean',
				'default' => true,
			),
			'textColor'            => array(
				'type'    => 'string',
				'default' => '',
			),
			'linkTarget'           => array(
				'type'    => 'boolean',
				'default' => true,
			),
			'rssUrl'               => array(
				'type'    => 'string',
				'default' => '',
			),
			'rssBackgroundColor'   => array(
				'type'    => 'string',
				'default' => '#ffffff',
			),
			'rssTextMainColor'     => array(
				'type'    => 'string',
				'default' => '#cccccc',
			),
			'rssTextSubColor'      => array(
				'type'    => 'string',
				'default' => '#444444',
			),
			'titleElement'         => array(
				'type'    => 'string',
				'default' => 'h2',
			),
			'thumbnailPosition' => array(
				'type'    => 'string',
				'default' => 'top',
			),
			'thumbnailAspectRatio' => array(
				'type'    => 'string',
				'default' => '16-9',
			),
			'enableSlide' => array(
				'type'    => 'boolean',
				'default' => false,
			),
			'blockID'     => array(
				'type'    => 'string',
				'default' => '',
			),
		);

		register_block_type(
			Define::value( 'plugin_path' ) . 'build/rss',
			array(
				'attributes'      => $args,
				'render_callback' => array( $this, 'block_callback' ),
			)
		);
	}

	/**
	 * 出力（コールバック）
	 *
	 * @param array $attributes 属性
	 * @return string
	 */
	public function block_callback( $attributes ) {
		$rss_data   = '';
		$class = '';
		$textcolor         = $attributes['textColor'];

		if ( empty( $attributes['rssUrl'] ) ) {
			return false;
		}

		// タイトル属性
		if ( ! empty( $attributes['titleElement'] ) ) {
			$title_element = $attributes['titleElement'];
		}

		// delete_transient( Define::value( 'plugin_func_name' ) . '_rss_feed_' . get_the_ID() . '_' . $attributes['rssUrl'] );

		// $excerpt = $attributes['displayExcerpt'];

		// アイテムデータをキャッシュして、なかったらループで取得して配列に入れる
		$items_data = get_transient( Define::value( 'plugin_func_name' ) . '_rss_feed_' . get_the_ID() . '_' . $attributes['rssUrl'] );

		if ( false === $items_data ) {
			// キャッシュがなかったら取りに行く
			$rss = fetch_feed( $attributes['rssUrl'] );

			if ( is_wp_error( $rss ) ) {
				return 'RSS フィードの URL が正しくありません。';
			}

			// 連想配列に入れる
			// $thumbnail,$author,$date,$title

			$maxitems  = $rss->get_item_quantity( 10 );
			$rss_items = $rss->get_items( 0, $maxitems );

			$items_data = array();

			foreach ( $rss_items as $item ) {
				// $output .= $item->get_description();

				$thumbnail = '';

				// rss のthumbnailから取得
				if ( '' === $thumbnail ) {
					$thumbnail_tags = $item->get_item_tags( '', 'thumbnail' );
					if ( ! empty( $thumbnail_tags ) ) {
						// $thumbnail_url = $thumbnail_tags[0]['child']['']['url'][0]['data'];
						$thumbnail_url = $thumbnail_tags[0]['data'];
						if ( ! empty( $thumbnail_url ) ) {
							$thumbnail = $thumbnail_url;
						}
					}
				}

				// rss のenclosureから取得
				if ( '' === $thumbnail ) {
					$enclosure = $item->get_enclosure();
					if ( $enclosure && ! empty( $enclosure->thumbnails[0] ) ) {
						$thumbnail = $enclosure->thumbnails[0];
					}
				}

				// OGPから取得
				if ( '' === $thumbnail ) {
					$request = wp_remote_get( $item->get_link() );

					if ( ! is_wp_error( $request ) ) {
						if ( isset( $request ) && ! empty( $request ) && 200 === $request['response']['code'] ) {
							if ( preg_match( '/<meta.+?(property|name)=["\'](og:image|twitter:image)["\'][^\/>]*?content=["\']([^"\']+?)["\'].*?\/?>/is', $request['body'], $matches ) ) {
								if ( $matches[3] ) {
									$thumbnail = $matches[3];
								} else {
									$thumbnail = $this->get_content_image( $request['body'] );
								}
							} else {
								$thumbnail = $this->get_content_image( $request['body'] );
							}
						} else {
							$thumbnail = $this->get_content_image( $request['body'] );
						}
					}
				}

				$items_data[] = array(
					'title'     => $item->get_title(),
					'link'      => $item->get_permalink(),
					'date'      => $item->get_date( get_option( 'date_format' ) ),
					'author'    => ( is_object( $item->get_author() ) ? wp_strip_all_tags( $item->get_author()->get_name() ) : '' ),
					'thumbnail' => $thumbnail,
				);

				// print_r($items_data);
				set_transient( Define::value( 'plugin_func_name' ) . '_rss_feed_' . get_the_ID() . '_' . $attributes['rssUrl'], $items_data, 60 * 60 * 12 );
			}
		}

		if( $items_data ){
			// レイアウト別にテンプレート読み込み
			switch ( $attributes['layout'] ) {
				case 'list':
					return $this->list( $items_data, $attributes );
					// break;
				default:
					return $this->grid( $items_data, $attributes );
			}
		}	
	}

	/**
	 * グリッドレイアウト
	 *
	 * @param array    $items_data 取得データ
	 * @param array    $attributes 属性
	 * @return mixed
	 */
	public function grid( $items_data, $attributes ) {
		$class             = '';
		$json              = '';
		$padding_array     = array();
		$posts_styles      = '';
		$id                = ' id="block-' . $attributes['blockID'] . '" ';
		$column            = ' columns-' . absint( $attributes['columns'] );
		$textcolor         = $attributes['textColor'];
		$i                 = 0;

		// タイトル属性
		if ( ! empty( $attributes['titleElement'] ) ) {
			$title_element = $attributes['titleElement'];
		}

		// スライダーを有効にしている場合
		if ( $attributes['enableSlide'] ) {

			$column       = '';
			$slider_class = ' class="swiper-slide"';

			$data = array(
				'blockID'   => $attributes['blockID'],
				'effect'    => $attributes['effect'],
				'direction' => $attributes['direction'],
			);

			if ( ! empty( $attributes['slidesPerView'] ) ) {
				$data['slidesPerView'] = $attributes['slidesPerView'];
			}

			if ( ! empty( $attributes['loop'] ) ) {
				$data['loop'] = $attributes['loop'];
			}

			// エフェクト「キューブ」のシャドウを無効
			if ( 'cube' === $attributes['effect'] ) {
				$data['cubeEffect'] = array(
					'shadow'       => false,
					'slideShadows' => false,
				);
			}

			// エフェクト「フリップ」のシャドウを無効
			if ( 'flip' === $attributes['effect'] ) {
				$data['flipEffect'] = array(
					'slideShadows' => false,
				);
			}

			// エフェクト「フェード」のクロスフェードを有効
			if ( 'fade' === $attributes['effect'] ) {
				$data['fadeEffect'] = array(
					'crossFade' => true,
				);
			}

			// エフェクト「カバーフロー」のシャドウを無効
			if ( 'coverflow' === $attributes['effect'] ) {
				$data['coverflowEffect'] = array(
					'slideShadows' => false,
				);
			}

			// エフェクト「スライド」「カバーフロー」のみ
			if ( 'slide' === $attributes['effect'] || 'coverflow' === $attributes['effect'] ) {
				// Spacebetween
				$data['spaceBetween'] = $attributes['spaceBetween'];

				// slidesPerView
				if ( ! empty( $attributes['slidesPerView'] ) ) {
					$data['slidesPerView'] = $attributes['slidesPerView'];
				}

				// CenterSlides
				if ( true === $attributes['centeredSlides'] ) {
					$data['centeredSlides'] = $attributes['centeredSlides'];
				}

				// Group
				if ( ! empty( $attributes['slidesPerGroup'] ) ) {
					$data['slidesPerGroup'] = $attributes['slidesPerGroup'];

					if ( true === $attributes['loop'] ) {
						$data['loopFillGroupWithBlank'] = $attributes['loop'];
					}
				}

				// Responsive
				if ( true === $attributes['responsive'] ) {

					// 681
					if ( ! empty( $attributes['breakPointSmartphoneSlidesPreview'] ) ) {
						$data['breakpoints'][681]['slidesPerView'] = $attributes['breakPointSmartphoneSlidesPreview'];
					}

					if ( ! empty( $attributes['breakPointSmartphoneSpaceBetween'] ) ) {
						$data['breakpoints'][681]['spaceBetween'] = $attributes['breakPointSmartphoneSpaceBetween'];
					}

					if ( ! empty( $attributes['breakPointSmartphoneslidesPerGroup'] ) ) {
						$data['breakpoints'][681]['slidesPerGroup'] = $attributes['breakPointSmartphoneslidesPerGroup'];
					}

					// 769
					if ( ! empty( $attributes['breakPointTabletSlidesPreview'] ) ) {
						$data['breakpoints'][769]['slidesPerView'] = $attributes['breakPointTabletSlidesPreview'];
					}

					if ( ! empty( $attributes['breakPointTabletSpaceBetween'] ) ) {
						$data['breakpoints'][769]['spaceBetween'] = $attributes['breakPointTabletSpaceBetween'];
					}

					if ( ! empty( $attributes['breakPointTabletslidesPerGroup'] ) ) {
						$data['breakpoints'][769]['slidesPerGroup'] = $attributes['breakPointTabletslidesPerGroup'];
					}
				}
			}

			// Speed
			$data['speed'] = $attributes['speed'] * 1000;

			// Direction
			$data['direction'] = $attributes['direction'];

			// Autoplay
			if ( true === $attributes['autoplay'] ) {
				$data['autoplay']['delay'] = $attributes['autoplayDelay'] * 1000;

				if ( true === $attributes['autoplayReverseDirection'] ) {
					$data['autoplay']['reverseDirection'] = $attributes['autoplayReverseDirection'];
				}

				if ( false === $attributes['autoplayDisableOnInteraction'] ) {
					$data['autoplay']['disableOnInteraction'] = $attributes['autoplayDisableOnInteraction'];
				}
			}

			// Scrollbar
			if ( true === $attributes['scrollbar'] ) {
				$data['scrollbar']['el'] = '.swiper-scrollbar';
			}

			// Navigation
			if ( true === $attributes['navigation'] ) {
				$data['navigation']['nextEl'] = '.swiper-button-next';
				$data['navigation']['prevEl'] = '.swiper-button-prev';
			}

			if ( false === $attributes['scrollbar'] && 'progress' !== $attributes['paginationType'] && 'flip' !== $attributes['effect'] ) {
				// Loop
				if ( true === $attributes['loop'] ) {
					$data['loop'] = $attributes['loop'];
				}
			}

			// Pagination
			if ( true === $attributes['pagination'] ) {
				$data['pagination']['el']        = '.swiper-pagination';
				$data['pagination']['clickable'] = true;

				if ( 'dynamic' === $attributes['paginationType'] ) {
					$data['pagination']['dynamicBullets'] = true;
				}

				if ( 'progress' === $attributes['paginationType'] ) {
					$data['pagination']['type'] = 'progressbar';
				}

				if ( 'fraction' === $attributes['paginationType'] ) {
					$data['pagination']['type'] = 'fraction';
				}
			}

			// 最後に属性作る
			$json = htmlspecialchars( wp_json_encode( $data ), ENT_QUOTES );
		}

		//クラス名などの属性を作成
		if ( ! $attributes['enableSlide'] ) {
			$class .= 'articles';

			if ( isset( $attributes['align'] ) ) {
				if( 'wide' === $attributes['align'] ){
					$class .= ' alignwide';
				}
			}

			if ( isset( $attributes['layout'] ) ) {
				$class .= ' is-' . $attributes['layout'];
			}
	
			if ( isset( $attributes['columns'] ) && $attributes['columns'] > 1 ) {
				$class .= ' flex gap-8 columns-' . absint( $attributes['columns'] );
			}
	
			if ( isset( $attributes['thumbnailPosition'] ) ) {
				$class .= ' featured-image-' . $attributes['thumbnailPosition'];
			}
	
			if ( isset( $attributes['displayThumbnail'] ) ) {
				$class .= ' has-featured-image';
			}
		} else {
			$class .= 'is-slider';
		}

		// テキストカラー
		if ( $textcolor ) {
			$style = ' color:' . esc_attr( $textcolor );
		} else {
			$style = '';
		}

		$linktarget = $attributes['linkTarget'];

		if ( $linktarget ) {
			$target = ' target="_blank" rel="noopener noreferrer"';
		} else {
			$target = '';
		}

		$wrapper_attributes = get_block_wrapper_attributes( 
			array( 
				'style' => $style,
				'class' => $class,
			)
		);

		if( $json ){
			$json = ' data-slider="' . $json . '" ';
		}

		$output = '<div ' . $id . $json . $wrapper_attributes . '>';

		$item_count = $attributes['numberOfItems'];
		if ( $attributes['numberOfItems'] > count( $items_data ) ) {
			$item_count = count( $items_data );
		}

		while ( $i < $item_count ) {
			$output .= '<article>';
			if ( $attributes['displayThumbnail'] ) {
				if ( ! empty( $items_data[ $i ]['thumbnail'] ) ) {
					$featured_image = $items_data[ $i ]['thumbnail'];
				} else {
					$featured_image = $this->get_default_image( $attributes['defaultImage'] );
				}

				$aspect_ratio = ' aspect-ratio-' . $attributes['thumbnailAspectRatio'];

				$output .= '<div class="post-image' . $aspect_ratio . '">';
				$output .= '<a' . $target . ' class="wp-block-rss-item" href="' . esc_url( $items_data[ $i ]['link'] ) . '">';
				$output .= '<figure><img src="' . esc_url( $featured_image ) . '" alt=""></figure>';
				$output .= '</a></div>';
			}
			$output .= '<div class="post-detail" ' . $style . '>';
			$output .= '<a class="post-link" href="' . esc_url( $items_data[ $i ]['link'] ) . '">';
			$output .= '<header><' . $title_element . ' class="post-title has-sm-font-size">' . esc_html( $items_data[ $i ]['title'] ) . '</' . $title_element . '></header>';
			$output .= '</a>';
			if ( $attributes['displayDate'] || $attributes['displayAuthor'] ) {
				$output .= '<footer class="has-2-xs-font-size">';
				if ( $attributes['displayDate'] ) {
					$output .= '<span class="date">' . esc_html( $items_data[ $i ]['date'] ) . '</span>';
				}
				if ( $attributes['displayAuthor'] ) {
					$output .= '<span class="author">' . esc_html( $items_data[ $i ]['author'] ) . '</span>';
				}
				$output .= '</footer>';
			}
			$output .= '</div>';
			$output .= '</article>';
			++$i;
		}

		$output .= '</div>';

		wp_reset_postdata();
		
		return wp_kses_post( $output );
	}

	/**
	 * グリッドレイアウト
	 *
	 * @param array    $items_data 取得データ
	 * @param array    $attributes 属性
	 * @return mixed
	 */
	public function list( $items_data, $attributes ) {
		$class             = '';
		$json              = '';
		$posts_styles      = '';
		$column            = ' columns-' . absint( $attributes['columns'] );
		$textcolor         = $attributes['textColor'];
		$border            = $attributes['listBorderStyle'];
		$i                 = 0;

		// タイトル属性
		if ( ! empty( $attributes['titleElement'] ) ) {
			$title_element = $attributes['titleElement'];
		}

		//クラス名などの属性を作成
		$class .= 'articles';

		if ( isset( $attributes['layout'] ) ) {
			$class .= ' is-' . $attributes['layout'];
		}

		if ( isset( $attributes['listLayoutType'] ) && '' !== $attributes['listLayoutType'] ) {
			$class .= ' is-list-' . $attributes['listLayoutType'];
		}

		// ボーダースタイル
		if ( 'none' !== $border ) {
			$class .= ' is-border is-border-' . esc_attr( $border );
		} else {
			$class .= '';
		}

		if ( isset( $attributes['thumbnailPosition'] ) && 'date' !== $attributes['listLayoutType'] ) {
			$class .= ' featured-image-' . $attributes['thumbnailPosition'];
		}

		if ( isset( $attributes['displayThumbnail'] ) && 'date' !== $attributes['listLayoutType'] ) {
			$class .= ' has-featured-image';
		}

		// テキストカラー
		if ( $textcolor ) {
			$style = ' color:' . esc_attr( $textcolor );
		} else {
			$style = '';
		}

		$wrapper_attributes = get_block_wrapper_attributes( 
			array( 
				'style' => $style,
				'class' => $class,
			)
		);

		$output = '<div ' . $wrapper_attributes . '>';

		$item_count = $attributes['numberOfItems'];
		if ( $attributes['numberOfItems'] > count( $items_data ) ) {
			$item_count = count( $items_data );
		}

		$linktarget = $attributes['linkTarget'];

		if ( $linktarget ) {
			$target = ' target="_blank" rel="noopener noreferrer"';
		} else {
			$target = '';
		}

		while ( $i < $item_count ) {
			$output .= '<article>';
			if( $attributes['listLayoutType'] !== 'date' ){
				if ( $attributes['displayThumbnail'] ) {
					if ( ! empty( $items_data[ $i ]['thumbnail'] ) ) {
						$featured_image = $items_data[ $i ]['thumbnail'];
					} else {
						$featured_image = $this->get_default_image( $attributes['defaultImage'] );
					}
	
					$aspect_ratio = ' aspect-ratio-' . $attributes['thumbnailAspectRatio'];
	
					$output .= '<div class="post-image' . $aspect_ratio . '">';
					$output .= '<a' . $target . ' class="wp-block-rss-item" href="' . esc_url( $items_data[ $i ]['link'] ) . '">';
					$output .= '<figure><img src="' . esc_url( $featured_image ) . '" alt=""></figure>';
					$output .= '</a></div>';
				}
			}

			if( $attributes['listLayoutType'] === 'date' ){
				if ( $attributes['displayDate'] ) {
					$output .= '<div class="post-date">';
					$output .= '<time class="date">' . esc_html( $items_data[ $i ]['date'] ) . '</time>';
					$output .= '</div>';
				}	
			}

			$output .= '<div class="post-detail" ' . $style . '>';
			$output .= '<a class="post-link" href="' . esc_url( $items_data[ $i ]['link'] ) . '">';
			$output .= '<header><' . $title_element . ' class="post-title has-sm-font-size">' . esc_html( $items_data[ $i ]['title'] ) . '</' . $title_element . '></header>';
			$output .= '</a>';
			if ( $attributes['displayDate'] || $attributes['displayAuthor'] ) {
				$output .= '<footer class="has-2-xs-font-size">';
				if ( $attributes['displayDate'] ) {
					$output .= '<time class="date">' . esc_html( $items_data[ $i ]['date'] ) . '</time>';
				}
				if ( $attributes['displayAuthor'] ) {
					$output .= '<span class="author">' . esc_html( $items_data[ $i ]['author'] ) . '</span>';
				}
				$output .= '</footer>';
			}
			$output .= '</div>';
			$output .= '</article>';
			++$i;
		}

		$output .= '</div>';

		wp_reset_postdata();
		
		return wp_kses_post( $output );
	}

	/**
	 * Get Contents First Image
	 *
	 * @param string $content 本文
	 * @return $thumbnail
	 */
	public function get_content_image( $content ) {
		ob_start();
		ob_end_clean();
		preg_match_all( '/<img.+src=[\'"]([^\'"]+)[\'"].*>/i', $content, $matches );

		if ( isset( $matches[1][0] ) && ! is_wp_error( $matches[1][0] ) ) {
			$thumbnail = $matches[1][0];
		} else {
			$thumbnail = '';
		}

		// print_r('コンテンツから取得');

		return $thumbnail;
	}

	/**
	 * Get Default Image
	 *
	 * @param string $default_image 画像 URL
	 * @return $thumbnail
	 */
	public function get_default_image( $default_image ) {
		$thumbnail = '';
		$noimageicon = '<svg xmlns="http://www.w3.org/2000/svg" class="icon icon-tabler icon-tabler-photo" width="24" height="24" viewBox="0 0 24 24" stroke-width="1.25" stroke="currentColor" fill="none" stroke-linecap="round" stroke-linejoin="round"><path stroke="none" d="M0 0h24v24H0z" fill="none"></path><line x1="15" y1="8" x2="15.01" y2="8"></line><rect x="4" y="4" width="16" height="16" rx="3"></rect><path d="M4 15l4 -4a3 5 0 0 1 3 0l5 5"></path><path d="M14 14l1 -1a3 5 0 0 1 3 0l2 2"></path></svg>';

		if ( $default_image ) {
			$thumbnail = $default_image;
		} elseif ( get_theme_mod( 'setting_archive_default_image', '' ) ) {
			$image      = get_theme_mod( 'setting_archive_default_image' );
			$image_id   = attachment_url_to_postid( $image );
			$image_data = wp_get_attachment_image_src( $image_id, 'thumbnail' );
			if ( true === $image_data[3] ) {
				$image_thumbnail = $image_data[0];
				$thumbnail       = $image_thumbnail;
			} else {
				$thumbnail = $image;
			}
		} else {
			$thumbnail .= '<div class="no-image">' . $noimageicon . '</div>';
		}

		// print_r('デフォルトから取得');
		return $thumbnail;
	}

}

use hakoniwa\blocks\ssr\rss\Register;
new Register();