React-native-snap-carousel: Is there a way to make an initial placeholder slide?

Created on 23 Mar 2018  路  13Comments  路  Source: meliorence/react-native-snap-carousel

Hi. I have the carousel all hooked up and working great. THANKS a ton for this component!

The last thing I'd like to do is conditionally render a first slide if more than one slide exists.
The line myProps.images[0] === image is an example of what I'm attempting to do.
Is this concept possible? Thanks!

   <Carousel
    data={myProps.images}
    sliderWidth={Dimensions.get('window').width}
    itemWidth={Dimensions.get('window').width * 0.8 + 8}
    keyExtractor={image => image.id}
    renderItem={({ item: image }) => (
      <View style={myStyles.carouselItemContainer}>
        {myProps.images[0] === image && <Text>THIS IS A SUMMARY SLIDE OF THE SLIDESHOW!! :-)</Text>}
        <ProgressiveImage
          blurredImageUrl={imageUrlThumbnailSized(image.url)}
          finalImageUrl={imageUrlPostSized(image.url)}
          blurRadiusStart={3}
          blurRadiusEnd={1}
          unBlurDuration={1000}
        />
      </View>
    )}
  />
feedback?

Most helpful comment

Note: I was wondering if I should just use a FlatList instead of a RN snap carousel. I found a blog post that says you can achive a similar result as a carousel with just a few additional properties on the FlatList:

            snapToAlignment={"start"}
            snapToInterval={this.IMAGE_WIDTH + 10}
            decelerationRate={"fast"}
            pagingEnabled

I guess as long as I don't need any fancy effects on the carousel! So I will have to try this next.

All 13 comments

Hi @GollyJer,

Unless I haven't properly understood your need, it should be as simple as the following:

renderItem={({ item: image }) => (
    const child = myProps.images[0] === image ? (
            <Text>THIS IS A SUMMARY SLIDE OF THE SLIDESHOW!! :-)</Text>
    ) : (
        <ProgressiveImage
          blurredImageUrl={imageUrlThumbnailSized(image.url)}
          finalImageUrl={imageUrlPostSized(image.url)}
          blurRadiusStart={3}
          blurRadiusEnd={1}
          unBlurDuration={1000}
        />
    );
    return (
        <View style={myStyles.carouselItemContainer}>
            { child }
        </View>
    )
)}

@bd-arc Thanks for the reply. I didn't explain myself very clearly... sorry.

As an example... if there are 3 images I want to render 4 slides.
[title slide] [image1] [image2] [image3]

So some way of saying "when there are more than one slide, put an extra title slide at the front".

Since the carousel extends the FlatList component, you can take advantage of the inherited ListHeaderComponent prop. Something along those lines:

const header = data.length >= 3 ? <TitleSlide /> : false;

return (
    <Carousel
      // other props
      ListHeaderComponent={header}
    />
);

@bd-arc thanks so much for the helpful ideas!
It didn't quite work but got a lot closer.

_This is a test app with test images..._
Here's an example with three slides.
20180325_123445

And here is test with a 4th slide "Title" slide added in the ListHeaderComponent prop.
You'll notice the visible depth of the primary slides is lower and I'm unable to scroll to the last slide.
20180325_123740

Not sure there's much else to try.
Thanks again for the help you've provided.

@GollyJer Damn, sorry! Of course it can't work since I've never thought about taking the header and footer into account for index handling... The bright side though is that's an update I'm now considering ;-)

For now, do you have any way of altering your dataset if it contains more than two items? For example, you can prepend some specific data for your title item and then render this one conditionally in renderItem().

render () {
    const data = myProps.images;

    if (data.length >= 3) {
        data.unshift({
            type: 'title',
            // other useful data
        });
    }

    return (
        <Carousel
          data={data}
          renderItem={({ item: image }) => (
              const child = item.type && item.type === 'title' ? (
                      <Text>THIS IS A SUMMARY SLIDE OF THE SLIDESHOW!! :-)</Text>
              ) : (
                  <ProgressiveImage
                  blurredImageUrl={imageUrlThumbnailSized(image.url)}
                  finalImageUrl={imageUrlPostSized(image.url)}
                  blurRadiusStart={3}
                  blurRadiusEnd={1}
                  unBlurDuration={1000}
                  />
              );
              return (
                  <View style={myStyles.carouselItemContainer}>
                      { child }
                  </View>
              );
          )}
        />
    );
}

@bd-arc You've given me an idea. I'll let you know how it goes.

taking the header and footer into account for index handling...

This would be a simple way for users to optionally add leading and trailing slides... +1. 馃槃

Hi @GollyJer,

Any news regarding this issue?

Closing as no further feedback was provided.

@bd-arc Is ListHeaderComponent supported now?

@srameshr Unfortunately no.

I haven't been able to find a way to handle it properly without generating side effects.

I'm trying to understand why this would be problematic. The main reason I want the header is that the header is not meant to be the same size (using vertical slider, so height) as the other elements. But I would like the position of each element to end up at the same y-location, which actually it's not doing that either right now, even without a header (there's a slight "drift" in the y-location of each card.

Note: I was wondering if I should just use a FlatList instead of a RN snap carousel. I found a blog post that says you can achive a similar result as a carousel with just a few additional properties on the FlatList:

            snapToAlignment={"start"}
            snapToInterval={this.IMAGE_WIDTH + 10}
            decelerationRate={"fast"}
            pagingEnabled

I guess as long as I don't need any fancy effects on the carousel! So I will have to try this next.

Oh I totally agree: if you don't need any kind of advanced feature or effect, you'll be better off with a regular FlatList, particularly since they made the snapToInterval prop available on Android as well ;-)

Was this page helpful?
0 / 5 - 0 ratings