Skip to content

Commit 4f4cd38

Browse files
committed
Merge branch 'develop'
2 parents 5a4f847 + ef0a94b commit 4f4cd38

17 files changed

+26612
-287
lines changed

.babelrc

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{
2+
"presets": ["env", "react"]
3+
}

.eslintrc.json

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
{
2+
"env": {
3+
"browser": true,
4+
"es6": true
5+
},
6+
"extends": "eslint:recommended",
7+
"parserOptions": {
8+
"ecmaFeatures": {
9+
"experimentalObjectRestSpread": true,
10+
"jsx": true
11+
},
12+
"sourceType": "module"
13+
},
14+
"plugins": [
15+
"react"
16+
],
17+
"rules": {
18+
"indent": [
19+
"error",
20+
2
21+
],
22+
"linebreak-style": [
23+
"error",
24+
"unix"
25+
],
26+
"quotes": [
27+
"error",
28+
"single"
29+
],
30+
"no-unused-vars": [
31+
"warn"
32+
]
33+
}
34+
}

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,3 +57,4 @@ typings/
5757
# dotenv environment variables file
5858
.env
5959

60+
.DS_Store

.npmignore

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
tests/
2+
.babelrc
3+
.eslintrc.json
4+
.travis.yml
5+
Test.js
6+
postcss.config.js
7+
webpack.config.js

.travis.yml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
language: node_js
2+
node_js:
3+
- "8"
4+
- "9"

README.md

Lines changed: 114 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,117 @@
11
# react-card-flipper
2-
A React card flipper component.
2+
[![Build Status](https://travis-ci.org/factor1/react-card-flipper.svg?branch=master)](https://travis-ci.org/factor1/react-card-flipper)
3+
[![npm version](https://badge.fury.io/js/react-card-flipper.svg)](https://badge.fury.io/js/react-card-flipper)
4+
![GitHub issues](https://img.shields.io/github/issues-raw/factor1/react-card-flipper.svg)
5+
![license](https://img.shields.io/github/license/factor1/react-card-flipper.svg)
36

4-
## Installation
7+
8+
A React card flipper component (built with React `16.2.0`) that can be triggered by hover or click. Inspired
9+
from [David Walsh's great tutorial](https://davidwalsh.name/css-flip).
10+
11+
## Installation
12+
### Yarn:
513
`yarn add react-card-flipper`
14+
15+
### npm:
16+
`npm install react-card-flipper --save`
17+
18+
## Current Browser Support
19+
Initial testing via BrowserStack of a React app that simply renders the card
20+
component.
21+
22+
| Browser | Support | Notes |
23+
| ---------------- |:--:| ------ |
24+
| Chrome >= 38 || |
25+
| Edge >= 14 || |
26+
| Firefox >= 16 | ✅‍ | |
27+
| IE 11-10 | ⚠️ | Card flips have no animation |
28+
| IE 9.0 || No toggling of cards |
29+
| Opera >= 30 || |
30+
| Safari >= 6.2.8 || |
31+
| Safari 6.0.5 | ⚠️ | Card flips have no animation |
32+
33+
34+
## Getting Started
35+
You can import react-card-flipper into your React app. The following is a bare
36+
bones example.
37+
38+
> **Important:** The `<ReactCardFlipper>` component must have two `<div>` elements, one for the front and one for the back.
39+
40+
```js
41+
import React from 'react';
42+
import ReactDOM from 'react-dom';
43+
import ReactCardFlipper from 'react-card-flipper';
44+
45+
ReactDOM.render(
46+
<div>
47+
<ReactCardFlipper>
48+
<div>
49+
The cards front content goes here.
50+
</div>
51+
<div>
52+
The cards back content goes here.
53+
</div>
54+
</ReactCardFlipper>
55+
</div>,
56+
document.getElementById('root')
57+
);
58+
```
59+
60+
## Props and Options
61+
The `ReactCardFlipper` component has 4 props it accepts that you can use to adjust
62+
how your card behaves.
63+
64+
| Prop / Option | Accepted Prop(s) | Default | Description |
65+
| ------------- |:---------------------------:|:-------:| ----------- |
66+
| `width` | String (ex: `300px`) | `auto` | Card width. |
67+
| `height` | String (ex: `600px`) | `auto` | Card height. |
68+
| `behavior` | String (`click` or `hover`) | `click` | If the card should click to flip, or hover to flip. |
69+
| `levitate` | Boolean | `false` | If the card should "levitate" up on hover. Only applied when `behavior` is `click`. |
70+
71+
#### Example:
72+
```js
73+
render() {
74+
return(
75+
<div>
76+
<ReactCardFlipper width="300px" height="550px" behavior="click" levitate={true}>
77+
<div>
78+
<h3>Click me to learn more</h3>
79+
</div>
80+
<div>
81+
<p>You Clicked!</p>
82+
</div>
83+
</ReactCardFlipper>
84+
</div>
85+
)
86+
}
87+
```
88+
89+
## Styling
90+
Out of the box we provide very little styling aside from core styles like transitions
91+
to let you shape the design as you see fit. All of the css classes provided for are
92+
prefixed with `rcf-` to avoid any conflicts with existing classes. In most cases you'll
93+
only be adding styles to `.rcf-front` & `.rcf-back`. All classes available for styling are:
94+
95+
- `rcf-container` - main container for the component
96+
- `rcf-front` - front card styling
97+
- `rcf-back` - back card styling
98+
- `rcf-flipper` - "flipper" container, controls animation speed, etc.
99+
100+
## Development
101+
To get started developing on this project, fork or clone the repo. Then run `yarn install`
102+
103+
#### Start the development server
104+
##### `yarn start`
105+
Starts the development/test server and polls for changes.
106+
107+
#### Running EsLint
108+
##### `yarn lint`
109+
Lints `ReactCardFlipper.js` and outputs any warnings or errors.
110+
111+
#### Running Tests
112+
##### `yarn test`
113+
Runs EsLint, and builds the test output.
114+
115+
#### Running Test Build
116+
##### `yarn build`
117+
Compiles a new test build.

ReactCardFlipper.css

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
/**
2+
* ReactCardFlipper
3+
* Author: Eric Stout, https://factor1studios.com
4+
**/
5+
6+
.rcf-container {
7+
perspective: 1000px;
8+
transform-style: preserve-3d;
9+
width: auto;
10+
height: auto;
11+
transition: transform 500ms cubic-bezier(.18,.45,.11,.91);
12+
}
13+
14+
.rcf-front, .rcf-back {
15+
width: auto;
16+
height: auto;
17+
backface-visibility: hidden;
18+
transform-style: preserve-3d;
19+
position: absolute;
20+
top: 0;
21+
left: 0;
22+
}
23+
24+
.rcf-front {
25+
z-index: 2;
26+
}
27+
28+
.rcf-back {
29+
transform: rotateY(180deg);
30+
}
31+
32+
.rcf-flipper {
33+
transition: 0.6s;
34+
transform-style: preserve-3d;
35+
position: relative;
36+
}
37+
38+
.rcf-active .rcf-flipper {
39+
transform: rotateY(180deg);
40+
}
41+
42+
.rcf-levitate {
43+
transform: translateY(-15px);
44+
transition: transform 500ms cubic-bezier(.18,.45,.11,.91);
45+
}
46+
47+
/* IE Support for 11-10 */
48+
@media screen and (-ms-high-contrast: active), (-ms-high-contrast: none) {
49+
.rcf-active .rcf-back {
50+
transform: rotateY(0deg);
51+
}
52+
53+
.rcf-active .rcf-flipper {
54+
transform: rotateY(0deg);
55+
}
56+
57+
.rcf-active .rcf-front {
58+
transform: rotateY(180deg);
59+
}
60+
61+
.rcf-active .rcf-back {
62+
transform: rotateY(0deg);
63+
}
64+
65+
.rcf-front {
66+
transform: rotateY(0deg);
67+
}
68+
69+
.rcf-back {
70+
transform: rotateY(-180deg);
71+
}
72+
}

ReactCardFlipper.js

Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
/**
2+
* ReactCardFlipper
3+
* Author: Eric Stout, https://factor1studios.com
4+
*
5+
* Optional Props:
6+
* Width: string (default: auto)
7+
* Height: string (default: auto)
8+
* behavior: click, hover (default: click)
9+
* levitate: boolean (default: false, only works when behavior is set to `click`)
10+
**/
11+
12+
import React, { Component } from 'react';
13+
import './ReactCardFlipper.css';
14+
15+
class ReactCardFlipper extends Component {
16+
constructor(props) {
17+
super(props);
18+
19+
this.state = {
20+
isFlipped: false,
21+
width: this.props.width,
22+
height: this.props.height,
23+
behavior: this.props.behavior ? this.props.behavior : 'click',
24+
levitate: this.props.levitate ? this.props.levitate : false
25+
}
26+
27+
// bind this 🤙
28+
this.handleFlip = this.handleFlip.bind(this);
29+
this.handleMouseEvent = this.handleMouseEvent.bind(this);
30+
}
31+
32+
handleFlip(e) {
33+
e.currentTarget.classList.toggle('rcf-active');
34+
this.setState({
35+
isFlipped: this.state.isFlipped ? false : true
36+
})
37+
}
38+
39+
handleLevitate(e) {
40+
e.currentTarget.classList.toggle('rcf-levitate');
41+
}
42+
43+
handleMouseEvent(e) {
44+
if( this.state.behavior === 'hover' ) {
45+
return this.handleFlip(e);
46+
} else if ( this.state.behavior === 'click' && this.state.levitate ) {
47+
return this.handleLevitate(e);
48+
} else if ( this.state.behavior === 'click' ) {
49+
return
50+
}
51+
}
52+
53+
render(){
54+
const containerStyles = {
55+
width: this.state.width,
56+
height: this.state.height,
57+
}
58+
59+
return(
60+
<div className="rcf-container" style={containerStyles} onClick={ (e) => { if(this.state.behavior === 'click'){ this.handleFlip(e) }}} onMouseEnter={ (e) => { this.handleMouseEvent(e) }}
61+
onMouseLeave={ (e) => { this.handleMouseEvent(e) }}>
62+
<div className="rcf-flipper">
63+
<div className="rcf-front" style={containerStyles}>
64+
{this.props.children[0]}
65+
</div>
66+
<div className="rcf-back" style={containerStyles}>
67+
{this.props.children[1]}
68+
</div>
69+
</div>
70+
</div>
71+
)
72+
}
73+
}
74+
75+
export default ReactCardFlipper;

Test.js

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
import React from 'react';
2+
import ReactDOM from 'react-dom';
3+
import ReactCardFlipper from './ReactCardFlipper';
4+
5+
ReactDOM.render(
6+
<div id="main" className="container">
7+
<div className="row">
8+
<div className="col-10 text-center col-centered">
9+
<ReactCardFlipper width="300px" height="400px" behavior="click">
10+
<div className="text-center">
11+
You can click me, go ahead... Try it.
12+
</div>
13+
<div className="text-center">
14+
Great job! You win person of the year.
15+
</div>
16+
</ReactCardFlipper>
17+
<ReactCardFlipper width="300px" height="400px" behavior="hover">
18+
<div className="text-center">
19+
This is a second card because you can have multiple. This one hovers!
20+
</div>
21+
<div className="text-center">
22+
Great job! You win person of the day.
23+
</div>
24+
</ReactCardFlipper>
25+
<ReactCardFlipper width="300px" height="400px" behavior="click" levitate={true}>
26+
<div className="text-center">
27+
You can click me, and I levitate
28+
</div>
29+
<div className="text-center">
30+
Great job! You win person of the minute.
31+
</div>
32+
</ReactCardFlipper>
33+
</div>
34+
</div>
35+
</div>,
36+
document.getElementById('root')
37+
);

0 commit comments

Comments
 (0)