Skip to content

Commit

Permalink
Merge pull request #16 from berzniz/scroll_spy
Browse files Browse the repository at this point in the history
Add Scroll Spy to highlight current visible file
  • Loading branch information
berzniz authored May 11, 2018
2 parents 8e5cac1 + 4eca87e commit 7d467f1
Show file tree
Hide file tree
Showing 4 changed files with 70 additions and 10 deletions.
7 changes: 4 additions & 3 deletions src/js/components/branch.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,16 +2,17 @@ import React from 'react'
import TreeView from 'react-treeview'
import File from './file'

const Branch = ({ nodeLabel, list, href, hasComments }) => {
const Branch = ({ nodeLabel, list, href, hasComments, diffElement, visibleElement }) => {
if (href) {
return <File name={nodeLabel} href={href} hasComments={hasComments} />
const isVisible = (diffElement === visibleElement)
return <File name={nodeLabel} href={href} hasComments={hasComments} isVisible={isVisible} />
}

return (
<TreeView nodeLabel={nodeLabel} defaultCollapsed={false}>
{list.map(node => (
<span key={node.nodeLabel}>
<Branch {...node} />
<Branch {...node} visibleElement={visibleElement} />
</span>
))}
</TreeView>
Expand Down
7 changes: 5 additions & 2 deletions src/js/components/file.jsx
Original file line number Diff line number Diff line change
@@ -1,10 +1,13 @@
import React from 'react'
import fileIcons from 'file-icons-js'

const File = ({ name, href, hasComments }) => {
const highlightColor = '#ebebeb'
const transparentColor = 'transparent'

const File = ({ name, href, hasComments, isVisible }) => {
const className = fileIcons.getClassWithColor(name)
return (
<div className='github-pr-file'>
<div className='github-pr-file' style={{ background: isVisible ? highlightColor : transparentColor }}>
<span className={`icon ${className}`} />
<a href={href} className='link-gray-dark'>{name}</a> {hasComments ? ' 💬' : ''}
</div>
Expand Down
35 changes: 32 additions & 3 deletions src/js/components/tree.jsx
Original file line number Diff line number Diff line change
@@ -1,14 +1,43 @@
import React from 'react'
import Branch from './branch.jsx'
import { isElementVisible } from '../lib'

class Tree extends React.Component {
constructor (props) {
super(props)

this.onClose = this.onClose.bind(this)
this.onScroll = this.onScroll.bind(this)

this.state = {
show: true
show: true,
visibleElement: null
}
}

componentDidMount () {
window.addEventListener('DOMContentLoaded', this.onScroll, false)
window.addEventListener('load', this.onScroll, false)
window.addEventListener('scroll', this.onScroll, false)
window.addEventListener('resize', this.onScroll, false)
}

componentWillUnmount () {
window.removeEventListener('DOMContentLoaded', this.onScroll, false)
window.removeEventListener('load', this.onScroll, false)
window.removeEventListener('scroll', this.onScroll, false)
window.removeEventListener('resize', this.onScroll, false)
}

onScroll () {
const { visibleElement } = this.state
const { root } = this.props
const { diffElements = [] } = root
const nextVisibleElement = diffElements.find(isElementVisible)
if (nextVisibleElement !== visibleElement) {
this.setState({
visibleElement: nextVisibleElement
})
}
}

Expand All @@ -20,7 +49,7 @@ class Tree extends React.Component {

render () {
const { root } = this.props
const { show } = this.state
const { show, visibleElement } = this.state

if (!show) {
return null
Expand All @@ -31,7 +60,7 @@ class Tree extends React.Component {
<button onClick={this.onClose} className='close_button'></button>
{root.list.map(node => (
<span key={node.nodeLabel}>
<Branch {...node} />
<Branch {...node} visibleElement={visibleElement} />
</span>
))}
</div>
Expand Down
31 changes: 29 additions & 2 deletions src/js/lib.js
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,8 @@ export const createFileTree = () => {
})
const tree = {
nodeLabel: '/',
list: []
list: [],
diffElements: []
}

files.forEach(({ parts, href }, fileIndex) => {
Expand All @@ -51,7 +52,15 @@ export const createFileTree = () => {
let node = location.list.find(node => node.nodeLabel === part)
if (!node) {
const hasComments = (hasCommentsForFileIndex(fileIndex) > 0)
node = { nodeLabel: part, list: [], href: (index === parts.length - 1) ? href : null, hasComments }
const diffElement = document.getElementById(`diff-${fileIndex}`)
tree.diffElements.push(diffElement)
node = {
nodeLabel: part,
list: [],
href: (index === parts.length - 1) ? href : null,
hasComments,
diffElement
}
location.list.push(node)
}
location.list = location.list.sort(sorter)
Expand All @@ -63,3 +72,21 @@ export const createFileTree = () => {
count: fileInfo.length
}
}

export const isElementVisible = (el) => {
if (!el) {
return false
}

const GITHUB_HEADER_HEIGHT = 60

const rect = el.getBoundingClientRect()

const windowHeight = (window.innerHeight || document.documentElement.clientHeight)
const windowWidth = (window.innerWidth || document.documentElement.clientWidth)

const vertInView = (rect.top <= windowHeight) && ((rect.top + rect.height) >= GITHUB_HEADER_HEIGHT)
const horInView = (rect.left <= windowWidth) && ((rect.left + rect.width) >= 0)

return (vertInView && horInView)
}

0 comments on commit 7d467f1

Please sign in to comment.