Ini akan menjadi pembunuh jika ada backend sentuh yang akan diaktifkan secara otomatis untuk perangkat sentuh.
Memang! Saya akan memeriksanya minggu depan.
Saya melakukan sesuatu seperti ini menggunakan pointer-events: none; sehingga elemen di bawah item yang sedang diseret bisa menangkap kejadian yang diarahkan mouse; Saya tertarik untuk melihat cara lain apa yang bisa dilakukan untuk mengatasi hal ini
Apa itu pustaka seret dan lepas yang canggih menggunakan touchmove? jQuery UI? Kita perlu melihat solusi yang baik dan mengadopsi triknya.
Saya belum pernah menggunakan semua ini pada proyek tetapi Googling menemukan:
Saya pikir akan lebih baik dan dalam semangat perpustakaan ini untuk menghindari manipulasi DOM (seperti yang dilakukan libs populer, apakah dengan mengkloning node untuk pratinjau, mengubah translateX / Y-nya, dll), dan sebagai gantinya membiarkan konsumen menggambar "drag layer" dan memberikan data yang diperlukan konsumen untuk ini.
Dengan kata lain jika Card
komponen diseret dengan backend sentuh, react-dnd tidak akan mencoba memindahkannya sendiri. Terserah Anda untuk merender beberapa komponen "lapisan" di bagian atas aplikasi Anda. Komponen ini akan menggunakan DragLayerMixin
disediakan oleh react-dnd untuk mempelajari tentang elemen saat ini, posisinya, dll. Komponen ini memutuskan bagaimana membuat item yang diseret berdasarkan tipenya dan juga 100% React.
var App = React.createClass({
render() {
return (
<div>
{this.props.activeRouteHandler />
<DragDropLayer />
</div>
);
}
});
var { DragLayerMixin } = require('react-dnd');
var DragDropLayer = React.createClass({
mixins: [DragLayerMixin],
render() {
// With non-native dragging backend, rendering items in the process of dragging is your responsibility.
// It's up to you to use translate3d or top/left, render thumbnails or real components, etc.
var {
draggedItem,
draggedItemType,
clientX,
clientY
} = this.getDragLayerState(); // provided by mixin
if (!draggedItem) {
return null;
}
return (
<div style={{zIndex: 10000, pointerEvents: 'none', position: 'absolute'}}>
{draggedItem &&
<div style={{transform: `translate3d(${clientX}, ${clientY}, 0)`}}>
{this.renderItem(draggedItemType, draggedItem)}
</div>
}
</div>
);
},
renderItem(type, item) {
// It's completely up to the consumer to specify how to render different types
switch (type) {
case ItemTypes.Card:
return <Card title={item.title} />;
case ItemTypes.List:
return <img src='thumbnail.jpg' />;
}
});
BTW pendekatan ini membuka kemungkinan yang sangat keren karena _untuk beberapa apps_ drag layer _adalah_ yang berisi item draggable. Drag layer tidak harus _harus_pisah, meskipun bisa, jika perlu.
Untuk aplikasi di mana item diseret ke beberapa penampung, penampung ini dapat menggunakan DragLayerMixin
dan mempelajari tentang posisi seret saat ini dan memindahkan elemen nyata saat seret terjadi:
Untuk aplikasi seperti Trello di mana item diseret melintasi layar melintasi penampung yang berbeda, akan berguna untuk memiliki komponen tingkat atas yang terpisah menggunakan DragLayerMixin
untuk merender item yang benar-benar diposisikan saat ini diseret.
Ini sangat masuk akal. Hampir semua browser, baik desktop atau seluler, harus dapat menganimasikan item di sekitar layar dengan lancar. Ini akan memudahkan untuk menambahkan efek 3d keren seperti yang dilakukan Trello saat memindahkan kartu.
Ini juga akan memungkinkan pengaturan kursor mouse sambil menyeret dan rendering placeholder yang lebih fleksibel ... Hal-hal yang tidak dapat Anda lakukan dengan api DND asli
Saya baru menyadari bahwa kami _also_ membuat API "seret lapisan" ini tersedia untuk API D&D browser. Cukup setel dragImage
ke piksel transparan seperti dalam contoh ini dan gambar apa pun yang Anda inginkan.
@nelix @KyleAMathews
Saya memiliki bukti konsep di sini: http://gaearon.github.io/react-dnd/#/drag -around-eksperimental
Ini akan berkedip saat Anda memindahkannya :-) (belum berfungsi di Firefox)
Kode sumber yang relevan:
https://github.com/gaearon/react-dnd/blob/experiments/examples/_drag-around-experimental/Box.js#L69
Seperti yang Anda lihat, terserah konsumen untuk menggambar lapisan seret dan komponen di atasnya, jadi ini sangat fleksibel.
Saya akan mencoba menyelesaikan ini minggu ini sebagai batu loncatan untuk menyentuh dukungan, dan setelah itu seharusnya tidak sulit untuk melakukan hal yang sama untuk mode sentuh.
Kami menggunakan lapisan seret seperti ini, tetapi kami menggunakan onMouseMove dll sehingga Anda dapat mengubah kursor mouse ...
Perhatian kecil tapi sangat penting bagi kami. Ini juga memungkinkan penggunaan untuk menggunakan sebagian besar kode yang sama untuk acara sentuh dan penunjuk.
Masih hal-hal DragLayer adalah langkah ke arah yang benar bagi saya, setelah Anda menyentuh dukungan, saya bersedia untuk mencoba dan memperluasnya untuk mendukung peristiwa penunjuk dan mouse jika Anda tertarik untuk memilikinya sebagai fitur?
Saya ingin memiliki API D&D HTML5 sebagai backend default dan kemudian memilih backend berbasis sentuhan / mousemove-based.
HTML5 D & D akan menjadi yang paling sederhana (tidak perlu drag layer, semuanya dikelola oleh browser). Memilih untuk mousemove / touchmove akan mengharuskan Anda menerapkan lapisan seret untuk menggambar apa pun yang Anda suka.
Masuk akal?
Tentu, itulah yang kuharapkan akan terjadi.
HTML5 D & D cepat dan (selain kebiasaan) cukup mudah digunakan sehingga ini adalah pilihan yang jelas secara default.
Jadi saya baru saja meminta untuk mengaktifkan sentuhan seret dan lepas ini. Adakah yang melakukan ini dan ingin berbagi tip?
@Tokopedia
@nelix mulai mengerjakan mousemove
backend, setelah itu kami akan membuat touchmove
backend.
Anda dapat melihat pekerjaan yang sedang berlangsung di sini: https://github.com/nelix/react-dnd/commit/8de7f7fe24c7ae397a971c517dada9323e6c27f0 (masih jauh dari selesai dan tidak benar-benar berfungsi pada saat ini). Kita masih perlu mencari tahu bagian mana yang tetap di DragDropMixin
dan mana yang perlu dipindahkan ke backends/HTML5
(dan backend lainnya).
Jika Anda ingin mengerjakannya, Anda bisa mulai dengan komit itu dan terus menerapkan backend mousemove. Saat berhasil, seharusnya tidak sulit untuk menerapkan backend touchmove yang serupa.
Harap, jika Anda ingin mengerjakan ini, terus beri tahu kami di sini atau di ruang Gitter, jadi kami tidak berakhir dengan dua penerapan.
Berikut adalah bukti konsep dukungan sentuh: https://github.com/gaearon/react-dnd/pull/143
Anda dapat bermain dengannya: http://rawgit.com/gaearon/react-dnd/touch-poc/examples/index.html
Ini menggunakan backend HTML5 di desktop dan sentuh backend di seluler.
Hanya contoh rendering kustom yang akan menampilkan pratinjau tarik di seluler.
Ini sepertinya cukup menjanjikan! Ada ide kapan ini akan mendarat? :)
Saat ini saya sibuk dengan proyek lain dan akan sampai Juli.
Saya mungkin dapat mengerjakan ini di suatu tempat pada bulan Juli atau Agustus, tetapi saya akan senang jika seseorang mengalahkan saya untuk itu :-)
sejak 1.1 disebutkan di utas ini dan v1.1.4 keluar. Saya hanya ingin tahu apakah bukti konsep di atas sudah termasuk dalam 1.1.4?
Nggak.
Saya seharusnya tidak menggunakan nomor versi yang tepat karena Anda tidak pernah tahu kapan Anda akan menabrak :-)
Saat ini saya tidak punya waktu untuk mengerjakan ini tetapi konsep buktinya ada di PR. Saya mungkin akan memperbarui PR untuk mencerminkan API saat ini dan menunggu seseorang untuk benar-benar menerapkannya.
Mari lanjutkan pembahasannya di https://github.com/gaearon/react-dnd/pull/240.
Bagi mereka yang datang setelah saya, inilah sepertinya jalan ke depan https://github.com/LouisBrunner/react-dnd-multi-backend
Saya menulis cuplikan ini:
function multiBackends(...backendFactories) {
return function(manager) {
const backends = backendFactories.map(b => b(manager));
return {
setup: (...args) =>
backends.forEach(b => b.setup.apply(b, args)),
teardown: (...args) =>
backends.forEach(b => b.teardown.apply(b, args)),
connectDropTarget: (...args) =>
backends.forEach(b => b.connectDropTarget.apply(b, args)),
connectDragPreview: (...args) =>
backends.forEach(b => b.connectDragPreview.apply(b, args)),
connectDragSource: (...args) =>
backends.forEach(b => b.connectDragSource.apply(b, args)),
};
};
}
Yang saya gunakan seperti ini:
DragDropContext(multiBackends(
ReactDnDHTML5Backend,
ReactDnDTouchBackend,
))
react-dnd-html5-backend
dan react-dnd-touch-backend
mendengarkan rangkaian acara yang terputus-putus. (dragstart, dragend, dragenter, dragleave dragover, dan drop vs touchstart, touchend dan touchmove).
Beberapa pengujian dasar dan berfungsi dengan baik, seret dan lepas saya sekarang mendukung peristiwa sentuh dan mouse secara bersamaan.
Apakah ada alasan mengapa itu tidak berhasil?
Komentar yang paling membantu
Bagi mereka yang datang setelah saya, inilah sepertinya jalan ke depan https://github.com/LouisBrunner/react-dnd-multi-backend