Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added a snap-to-mouse prop + documentation #204

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

7 changes: 7 additions & 0 deletions docs/assets/index-Rp5rmKIE.css

Large diffs are not rendered by default.

385 changes: 385 additions & 0 deletions docs/assets/index-Rw-YY1G1.js

Large diffs are not rendered by default.

7 changes: 0 additions & 7 deletions docs/assets/index.e8f83686.css

This file was deleted.

330 changes: 0 additions & 330 deletions docs/assets/index.ea9cf117.js

This file was deleted.

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

5 changes: 2 additions & 3 deletions docs/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -20,15 +20,14 @@
<meta itemprop="description" content="A Vue.js reliable, simple and touch-ready panes splitter / resizer.">
<title>Splitpanes</title>
<link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Roboto:100,300,400,500,700|Material+Icons">
<script type="module" crossorigin src="/splitpanes/assets/index.ea9cf117.js"></script>
<link rel="stylesheet" href="/splitpanes/assets/index.e8f83686.css">
<script type="module" crossorigin src="/splitpanes/assets/index-Rw-YY1G1.js"></script>
<link rel="stylesheet" crossorigin href="/splitpanes/assets/index-Rp5rmKIE.css">
</head>
<body>
<noscript>
<strong>We're sorry but the Splitpanes documentation doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
</noscript>
<a name="top"></a>
<div id="app"></div>

</body>
</html>
39 changes: 34 additions & 5 deletions src/components/splitpanes/splitpanes.vue
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,8 @@ export default {
pushOtherPanes: { type: Boolean, default: true },
dblClickSplitter: { type: Boolean, default: true },
rtl: { type: Boolean, default: false }, // Right to left direction.
firstSplitter: { type: Boolean }
firstSplitter: { type: Boolean },
snapToMouse: { type: Boolean, default: true }
},

provide () {
Expand All @@ -30,7 +31,11 @@ export default {
touch: {
mouseDown: false,
dragging: false,
activeSplitter: null
activeSplitter: null,
offset: { // Used to improve mouse following with thicker splitters
x: 0,
y: 0,
}
},
splitterTaps: { // Used to detect double click on touch devices.
splitter: null,
Expand Down Expand Up @@ -83,6 +88,7 @@ export default {

onMouseDown (event, splitterIndex) {
this.bindEvents()
this.calculateMouseOffset(event, splitterIndex)
this.touch.mouseDown = true
this.touch.activeSplitter = splitterIndex
},
Expand Down Expand Up @@ -153,14 +159,37 @@ export default {
this.$emit('pane-click', this.indexedPanes[paneId])
},

getMouseCoordinates (event) {
event = 'ontouchstart' in window && event.touches ? event.touches[0] : event
return { x: event.clientX, y: event.clientY }
},

// Get the cursor position relative to the splitpane container.
getCurrentMouseDrag (event) {
const rect = this.container.getBoundingClientRect()
const { clientX, clientY } = ('ontouchstart' in window && event.touches) ? event.touches[0] : event
const { x, y } = this.getMouseCoordinates(event)

return {
x: clientX - rect.left,
y: clientY - rect.top
x: x - rect.left + this.touch.offset.x,
y: y - rect.top + this.touch.offset.y,
}
},

// Stores the mouse position relative to the splitter.
// “snap to mouse” mode forces this to 0 so the splitter is always under it
calculateMouseOffset (event, splitterIndex) {
if (this.$props.snapToMouse) {
this.touch.offset = { x: 0, y: 0}
return
}

const splitter = this.container.querySelectorAll(':scope > .splitpanes__splitter')[splitterIndex]
const rect = splitter.getBoundingClientRect()
const { x, y } = this.getMouseCoordinates(event)

this.touch.offset = {
x: rect.left - x,
y: rect.top - y
}
},

Expand Down
81 changes: 80 additions & 1 deletion src/views/documentation.vue
Original file line number Diff line number Diff line change
Expand Up @@ -721,6 +721,78 @@
.splitpanes--vertical &gt; .splitpanes__splitter:before {left: -30px;right: -30px;height: 100%;}
.splitpanes--horizontal &gt; .splitpanes__splitter:before {top: -30px;bottom: -30px;width: 100%;}


//- Example
h3.mt12.pt8.mb2
a(href="#mouse-snapping") Mouse snapping
a(name="mouse-snapping")

p
| This example shows the effect of disabling splitters snapping to the mouse
| when the interacte zone is wider than a few pixels.

splitpanes.touch-example(
horizontal
style="height: 400px"
:snap-to-mouse="snapToMouse")
pane
splitpanes.touch-example(:snap-to-mouse="snapToMouse")
pane
span 1
pane
span 2
pane
span 3
pane
div.text
p
span(v-if="snapToMouse").
By default, the splitter always gets put under the cursor.
span(v-else).
When #[span.code :snap-to-mouse="false"], the splitter keeps its distance relative to the cursor.
br
w-button.mr2.mb2(@click="snapToMouse = !snapToMouse")
w-icon.ml-n1.mr1 material-icons {{ snapToMouse ? 'disable' : 'enable' }}
| {{ snapToMouse ? 'Disable' : 'Enable' }} mouse snapping

ssh-pre(language="html-vue" label="HTML").
&lt;splitpanes horizontal style="height: 400px" :snap-to-mouse="false"&gt;
&lt;pane&gt;
&lt;splitpanes&gt;
&lt;pane&gt;
&lt;span&gt;1&lt;/span&gt;
&lt;/pane&gt;
&lt;pane&gt;
&lt;span&gt;2&lt;/span&gt;
&lt;/pane&gt;
&lt;pane&gt;
&lt;span&gt;3&lt;/span&gt;
&lt;/pane&gt;
&lt;/splitpanes&gt;
&lt;/pane&gt;
&lt;pane&gt;
&lt;p&gt;When :snap-to-mouse="false", the splitter keeps its distance relative to the cursor.&lt;/p&gt;
&lt;/pane&gt;
&lt;/splitpanes&gt;

ssh-pre(language="css" label="CSS").
.splitpanes {background-color: #f8f8f8;}

.splitpanes__splitter {background-color: #ccc;position: relative;}
.splitpanes__splitter:before {
content: '';
position: absolute;
left: 0;
top: 0;
transition: opacity 0.4s;
background-color: rgba(255, 0, 0, 0.3);
opacity: 0;
z-index: 1;
}
.splitpanes__splitter:hover:before {opacity: 1;}
.splitpanes--vertical &gt; .splitpanes__splitter:before {left: -30px;right: -30px;height: 100%;}
.splitpanes--horizontal &gt; .splitpanes__splitter:before {top: -30px;bottom: -30px;width: 100%;}

//- Example.
h3.mt12.pt8.mb2
a(href="#do-your-own-style") Do your own style
Expand Down Expand Up @@ -813,6 +885,12 @@
code first-splitter
span.code.ml2 Default: false
p Displays the first splitter when set to true. This allows maximizing the first pane on splitter double click.
li
code snap-to-mouse
span.code.ml2 Default: true
p.
Always snap the splitter right under the mouse, even if the drag was started a few pixels of the center.
This makes more sense with custom themes and/or thicker splitter handles.

h2.mt12.pt12.mb2
a(href="#release-notes") Release Notes
Expand Down Expand Up @@ -890,7 +968,8 @@ export default {
paneSize: 50,
hidePane2: false,
horizontal: false,
firstSplitter: false
firstSplitter: false,
snapToMouse: true,
}),
methods: {
log (eventName, eventParams) {
Expand Down