Skip to content
This repository has been archived by the owner on Jan 10, 2023. It is now read-only.

Commit

Permalink
Merge pull request #32 from xwp/feature/23-popular_block
Browse files Browse the repository at this point in the history
[Gutenberg] Add Popular homepage block.
  • Loading branch information
kienstra authored Apr 12, 2018
2 parents c420080 + 216d27e commit 8f4c721
Show file tree
Hide file tree
Showing 5 changed files with 485 additions and 148 deletions.
5 changes: 5 additions & 0 deletions assets/css/editor-blocks.css

Large diffs are not rendered by default.

146 changes: 145 additions & 1 deletion assets/js/editor-blocks.js

Large diffs are not rendered by default.

218 changes: 72 additions & 146 deletions blocks/popular/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,148 +4,8 @@
* Internal block libraries.
*/
const { __ } = wp.i18n;
const { registerBlockType } = wp.blocks;

import { deamplify } from '../amp-transformer';

/**
* Render the popular block.
*
* @return {wp.element.Component} Rendered component.
*/
const renderStaticPopularBlock = () => {
return (
<section className='travel-popular pb4 pt3 relative'>
<header className='max-width-3 mx-auto px1 md-px2'>
<h3 className='h1 bold line-height-2 md-hide lg-hide' aria-hidden='true'>Top Adventures<br/>Near You</h3>
<h3 className='h1 bold line-height-2 xs-hide sm-hide center'>Top Adventures Near You</h3>
</header>
<div className='overflow-scroll'>
<div className='travel-overflow-container'>
<div className='flex px1 md-px2 mxn1'>
<div className='m1 mt3 mb2'>
<div className='travel-popular-tilt-right mb1'>
<div className='relative travel-results-result'>
<a className='travel-results-result-link block relative' href='#'>
<amp-img class='block rounded' width='346' height='200' noloading='' src={ travelGlobals.themeUrl + '/img/surf-day.jpg' } srcset={ travelGlobals.themeUrl + '/img/[email protected] 2x, ' + travelGlobals.themeUrl + '/img/surf-day.jpg 1x' }></amp-img>
</a>
<div className='travel-results-result-like absolute top-0 right-0'>
<div className='p1'>
<label className='travel-like'>
<input type='checkbox' className='absolute'/>
<div className='travel-like-hearts circle inline-block relative'>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart travel-like-heart-white absolute mx-auto '></div>
<div className='travel-like-heart travel-like-heart-solid absolute mx-auto '></div>
<div className='travel-like-heart travel-like-heart-outline absolute mx-auto '></div>
</div>
</label>
</div>
</div>
</div>
</div>

<div className='h2 line-height-2 mb1'>
<span className='travel-results-result-text'>Surf Day. Board and Wetsuits Included in Price!</span>
<span className='travel-results-result-subtext h3'></span>
<span className='travel-results-result-subtext h3'>$&nbsp;</span><span className='black bold'>100</span>
</div>

<div className='h4 line-height-2'>
<div className='inline-block relative mr1 h3 line-height-2'>
<div className='travel-results-result-stars green'>★★★★★</div>
</div>
<span className='travel-results-result-subtext mr1'>241 Reviews</span>
<span className='travel-results-result-subtext'><svg className='travel-icon' viewBox='0 0 77 100'><g fill='none' fillRule='evenodd'><path stroke='currentColor' strokeWidth='7.5' d='M38.794 93.248C58.264 67.825 68 49.692 68 38.848 68 22.365 54.57 9 38 9S8 22.364 8 38.85c0 10.842 9.735 28.975 29.206 54.398a1 1 0 0 0 1.588 0z'></path><circle cx='38' cy='39' r='10' fill='currentColor'></circle></g></svg> Oaxaca</span>
</div>
</div>
<div className='m1 mt3 mb2'>
<div className='travel-results-result relative mb1'>
<div className='relative travel-results-result'>
<a className='travel-results-result-link block relative' href='#'>
<amp-img class='block rounded' width='346' height='200' noloading='' src={ travelGlobals.themeUrl + '/imgdiscover-electronic-scene.jpg' } srcset={ travelGlobals.themeUrl + '/img/[email protected] 2x, ' + travelGlobals.themeUrl + '/img/discover-electronic-scene.jpg 1x' }></amp-img>
</a>
<div className='travel-results-result-flags absolute top-0 left-0'>
<div className='p1'><span className='travel-pill bold'>NEW</span></div>
</div>
<div className='travel-results-result-like absolute top-0 right-0'>
<div className='p1'>
<label className='travel-like'>
<input type='checkbox' className='absolute'/>
<div className='travel-like-hearts circle inline-block relative'>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart travel-like-heart-white absolute mx-auto '></div>
<div className='travel-like-heart travel-like-heart-solid absolute mx-auto '></div>
<div className='travel-like-heart travel-like-heart-outline absolute mx-auto '></div>
</div>
</label>
</div>
</div>
</div>
</div>

<div className='h2 line-height-2 mb1'>
<span className='travel-results-result-text'>Discover Oaxaca&lsquo;s Electronic Music Scene with a Top DJ</span>
<span className='travel-results-result-subtext h3'></span>
<span className='travel-results-result-subtext h3'>$&nbsp;</span><span className='black bold'>113</span>
</div>

<div className='h4 line-height-2'>
<div className='inline-block relative mr1 h3 line-height-2'>
<div className='travel-results-result-stars green'>★★★★★</div>
</div>
<span className='travel-results-result-subtext mr1'>42 Reviews</span>
<span className='travel-results-result-subtext'><svg className='travel-icon' viewBox='0 0 77 100'><g fill='none' fillRule='evenodd'><path stroke='currentColor' strokeWidth='7.5' d='M38.794 93.248C58.264 67.825 68 49.692 68 38.848 68 22.365 54.57 9 38 9S8 22.364 8 38.85c0 10.842 9.735 28.975 29.206 54.398a1 1 0 0 0 1.588 0z'></path><circle cx='38' cy='39' r='10' fill='currentColor'></circle></g></svg> Oaxaca</span>
</div>
</div>
<div className='m1 mt3 mb2'>
<div className='travel-popular-tilt-left mb1'>
<div className='relative travel-results-result'>
<a className='travel-results-result-link block relative' href='#'>
<amp-img class='block rounded' width='346' height='200' noloading='' src={ travelGlobals.themeUrl + '/img/skateboard-around-city.jpg' } srcset={ travelGlobals.themeUrl + '/img/[email protected] 2x, ' + travelGlobals.themeUrl + '/img/skateboard-around-city.jpg 1x' }></amp-img>
</a>
<div className='travel-results-result-like absolute top-0 right-0'>
<div className='p1'>
<label className='travel-like'>
<input type='checkbox' className='absolute'/>
<div className='travel-like-hearts circle inline-block relative'>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart-tiny travel-like-heart-solid absolute'></div>
<div className='travel-like-heart travel-like-heart-white absolute mx-auto '></div>
<div className='travel-like-heart travel-like-heart-solid absolute mx-auto '></div>
<div className='travel-like-heart travel-like-heart-outline absolute mx-auto '></div>
</div>
</label>
</div>
</div>
</div>
</div>

<div className='h2 line-height-2 mb1'>
<span className='travel-results-result-text'>Skateboard Around the City</span>
<span className='travel-results-result-subtext h3'></span>
<span className='travel-results-result-subtext h3'>$&nbsp;</span><span className='black bold'>92</span>
</div>

<div className='h4 line-height-2'>
<div className='inline-block relative mr1 h3 line-height-2'>
<div className='travel-results-result-stars green'>★★★★★</div>
</div>
<span className='travel-results-result-subtext mr1'>17 Reviews</span>
<span className='travel-results-result-subtext'><svg className='travel-icon' viewBox='0 0 77 100'><g fill='none' fillRule='evenodd'><path stroke='currentColor' strokeWidth='7.5' d='M38.794 93.248C58.264 67.825 68 49.692 68 38.848 68 22.365 54.57 9 38 9S8 22.364 8 38.85c0 10.842 9.735 28.975 29.206 54.398a1 1 0 0 0 1.588 0z'></path><circle cx='38' cy='39' r='10' fill='currentColor'></circle></g></svg> Mexico City</span>
</div>
</div>
</div>
</div>
</div>
</section>
);
};
const { registerBlockType, RichText } = wp.blocks;
const { Placeholder, withAPIData } = wp.components;

/**
* Register block.
Expand All @@ -162,11 +22,77 @@ export default registerBlockType(
__( 'Travel' )
],

edit() {
return deamplify( renderStaticPopularBlock() );
},
edit: withAPIData( () => {
return {
popularPosts: '/wp/v2/adventures?per_page=3&orderby=meta_value_num&meta_key=amp_travel_rating&_embed'
};
} )( ( { popularPosts } ) => { // eslint-disable-line
const popularPostsCount = 3;
const hasAdventures = Array.isArray( popularPosts.data ) && popularPosts.data.length;
if ( ! hasAdventures || popularPostsCount !== popularPosts.data.length ) {
return (
<Placeholder key='placeholder' icon='admin-post' label={ __( 'Adventures' ) } >
{ __( 'Not enough adventures with ratings found, add at least 3 to use the block.' ) }
</Placeholder>
);
}

const adventures = popularPosts.data;
const popularClasses = [
'travel-popular-tilt-right',
'travel-results-result',
'travel-popular-tilt-left'
];

return (
<section className='travel-popular pb4 pt3 relative'>
<header className='max-width-3 mx-auto px1 md-px2'>
<h3 className='h1 bold line-height-2'>{ __( 'Top Adventures' ) }</h3>
</header>
<div className='overflow-scroll'>
<div className='travel-overflow-container'>
<div className='flex px1 md-px2 mxn1'>
{ adventures.map( ( adventure, i ) => // eslint-disable-line
<div key='adventure' className='m1 mt3 mb2'>
<div className={ popularClasses[ i ] + ' mb1' }>
<div className='relative travel-results-result'>
<a className='travel-results-result-link block relative' href={ adventure.link }>
<img src={ adventure._embedded['wp:featuredmedia'][0].source_url } className='block rounded' width='346' height='200' ></img>
</a>
</div>
</div>

<div className='h2 line-height-2 mb1'>
<span className='travel-results-result-text'>{ adventure.title.rendered }</span>
<span className='travel-results-result-subtext h3'></span>
<span className='travel-results-result-subtext h3'>$&nbsp;</span><span className='black bold'>{ adventure.meta.amp_travel_price }</span>
</div>

<div className='h4 line-height-2'>
<div className='inline-block relative mr1 h3 line-height-2'>
<div className='travel-results-result-stars green'>
{ [ ...Array( parseInt( adventure.meta.amp_travel_rating ) ) ].map( () =>
'★'
) }
</div>
</div>
<span className='travel-results-result-subtext mr1'>{ adventure.meta.amp_travel_reviews } Reviews</span>
<span className='travel-results-result-subtext'><svg className='travel-icon' viewBox='0 0 77 100'><g fill='none' fillRule='evenodd'><path stroke='currentColor' strokeWidth='7.5' d='M38.794 93.248C58.264 67.825 68 49.692 68 38.848 68 22.365 54.57 9 38 9S8 22.364 8 38.85c0 10.842 9.735 28.975 29.206 54.398a1 1 0 0 0 1.588 0z'></path><circle cx='38' cy='39' r='10' fill='currentColor'></circle></g></svg>
{ adventure.meta.amp_travel_location }
</span>
</div>
</div>
) }
</div>
</div>
</div>
</section>
);
}),
save() {
return renderStaticPopularBlock();

// Handled by PHP.
return null;
}
}
);
125 changes: 124 additions & 1 deletion includes/class-amp-travel-blocks.php
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,13 @@
*/
class AMP_Travel_Blocks {

/**
* Number of popular posts to display.
*
* @var int
*/
public static $popular_posts_count = 3;

/**
* Init Travel Blocks.
*/
Expand All @@ -20,11 +27,127 @@ public function init() {
add_action( 'enqueue_block_editor_assets', array( $this, 'enqueue_editor_scripts' ) );
add_filter( 'the_content', array( $this, 'filter_the_content_amp_atts' ), 10, 1 );
add_filter( 'wp_kses_allowed_html', array( $this, 'filter_wp_kses_allowed_html' ), 10, 2 );
add_action( 'init', array( $this, 'register_block_travel_popular' ) );
add_action( 'init', array( $this, 'register_block_activity_list' ) );
add_action( 'init', array( $this, 'register_block_discover' ) );
}
}

/**
* Register Travel Popular block.
*/
public function register_block_travel_popular() {
if ( function_exists( 'register_block_type' ) ) {
register_block_type( 'amp-travel/popular', array(
'attributes' => array(
'heading' => array(
'type' => 'string',
'default' => __( 'Top Adventures', 'travel' ),
),
),
'render_callback' => array( $this, 'render_block_travel_popular' ),
) );
}
}

/**
* Frontend render for Popular block.
*
* @param array $attributes Block attributes.
* @return string Output.
*/
public function render_block_travel_popular( $attributes ) {
$output = '';

$adventures = get_posts(
array(
'post_type' => 'adventure',
'numberposts' => self::$popular_posts_count,
'orderby' => 'meta_value_num',
'meta_key' => 'amp_travel_rating',
)
);

if ( count( $adventures ) !== self::$popular_posts_count ) {
return $output;
}

$output .= '<section class="travel-popular pb4 pt3 relative">';

if ( ! empty( $attributes['heading'] ) ) {
$output .= '<header class="max-width-3 mx-auto px1 md-px2">
<h3 class="h1 bold line-height-2 md-hide lg-hide" aria-hidden="true">' . esc_html( $attributes['heading'] ) . '</h3>
<h3 class="h1 bold line-height-2 xs-hide sm-hide center">' . esc_html( $attributes['heading'] ) . '</h3>
</header>';
}

$output .= '<div class="overflow-scroll">
<div class="travel-overflow-container">
<div class="flex px1 md-px2 mxn1">';

$popular_classes = array(
'travel-popular-tilt-right',
'travel-results-result',
'travel-popular-tilt-left',
);

foreach ( $adventures as $index => $adventure ) {
$attachment_id = get_post_thumbnail_id( $adventure->ID );
$img_src = wp_get_attachment_image_url( $attachment_id, 'full' );
$img_srcset = wp_get_attachment_image_srcset( $attachment_id );
$price = get_post_meta( $adventure->ID, 'amp_travel_price', true );
$rating = round( (int) get_post_meta( $adventure->ID, 'amp_travel_rating', true ) );
$comments = wp_count_comments( $adventure->ID );
$locations = wp_get_post_terms( $adventure->ID, 'location', array(
'fields' => 'names',
) );

if ( is_wp_error( $locations ) || empty( $locations ) ) {
$location = '--';
} else {
$location = $locations[0];
}

$output .= '<div class="m1 mt3 mb2"><div class="' . esc_html( $popular_classes[ $index ] ) . ' mb1">
<div class="relative travel-results-result">
<a class="travel-results-result-link block relative" href="' . esc_url( get_the_permalink( $adventure->ID ) ) . '">
<amp-img class="block rounded" width="346" height="200" noloading="" src="' . esc_url( $img_src ) . '" srcset="' . esc_attr( $img_srcset ) . '"></amp-img>
</a>
</div>
</div>
<div class="h2 line-height-2 mb1">
<span class="travel-results-result-text">' . esc_html( get_the_title( $adventure->ID ) ) . '</span>
<span class="travel-results-result-subtext h3">•</span>
<span class="travel-results-result-subtext h3">$&nbsp;</span><span class="black bold">' . esc_html( $price ) . '</span>
</div>
<div class="h4 line-height-2">
<div class="inline-block relative mr1 h3 line-height-2">
<div class="travel-results-result-stars green">';

for ( $i = 0; $i < $rating; $i++ ) {
$output .= '';
}

$output .= '</div>
</div>
<span class="travel-results-result-subtext mr1">' .
/* translators: %d: The number of reviews */
sprintf( esc_html__( '%d Reviews', 'travel' ), esc_html( $comments->approved ) ) . '</span>
<span class="travel-results-result-subtext"><svg class="travel-icon" viewBox="0 0 77 100"><g fill="none" fillRule="evenodd"><path stroke="currentColor" strokeWidth="7.5" d="M38.794 93.248C58.264 67.825 68 49.692 68 38.848 68 22.365 54.57 9 38 9S8 22.364 8 38.85c0 10.842 9.735 28.975 29.206 54.398a1 1 0 0 0 1.588 0z"></path><circle cx="38" cy="39" r="10" fill="currentColor"></circle></g></svg>
' . esc_html( $location ) . '</span>
</div>
</div>';

}

$output .= '</div>
</div>
</div>
</section>';

return $output;
}

/**
* Register Travel Activity List block type.
*/
Expand Down Expand Up @@ -113,7 +236,7 @@ public function enqueue_editor_scripts() {
wp_enqueue_script(
'travel-editor-blocks-js',
get_template_directory_uri() . '/assets/js/editor-blocks.js',
array( 'wp-i18n', 'wp-element', 'wp-blocks', 'wp-components', 'wp-api' )
array( 'underscore', 'wp-i18n', 'wp-element', 'wp-blocks', 'wp-components', 'wp-api' )
);

wp_localize_script(
Expand Down
Loading

0 comments on commit 8f4c721

Please sign in to comment.