Drag-and-Drop — en interaktiv gest att dra ett visuellt objekt över skärmen med fingret. Gesten består av tre faser: fångst (long press eller beröring), förflyttning (fingerrörelse med objektet) och släpp (släpp i målzonen). Används för att ändra ordningen på element, flytta filer mellan mappar, organisera gränssnitt (drag to reorder, drag to resize). I iOS implementeras via UIDragInteraction, i Android via DragEvent och startDragAndDrop.
Huvudsakliga
Drag-and-Drop (DnD, dra och släpp) — en metod för att manipulera grafiska gränssnittselement där användaren fångar ett objekt med fingret eller musen, flyttar det till en annan position och släpper det. I mobila gränssnitt initieras Drag-and-Drop vanligtvis genom lång tryckning (Long Press) — användaren håller elementet i 300–500 ms, varefter systemet växlar gränssnittet till dragläge och fingerrörelsen för objektet med sig.
Historiskt uppträdde Drag-and-Drop i desktopgränssnitt (Xerox Star, 1981; Macintosh, 1984) som ett alternativ till kommandona kopiera/klistra in. På mobila plattformar uppträdde fullt stöd i iOS 11 (2017) med UIDragInteraction och i Android 7.0 (2016) med Multi-Window Drag-and-Drop. Innan dess implementerades dragning i mobila applikationer genom anpassade lösningar med gesture recognizers.
Nyckelkoncept: drag session (dragsession), drag items (dragna objekt), drag preview (visuell bild av objektet), drop target (släppzon), drop proposal (åtgärd vid släpp: flytta, kopiera, länka). Systemet hanterar sessionen på operativsystemsnivå, vilket möjliggör dragning av objekt mellan olika applikationer (t.ex. ett foto från Galleri till Anteckningar).
Drag-and-Drop delas in i tre på varandra följande faser. Fas 1 — fångst (Drag Start): användaren initierar gesten (vanligtvis Long Press), systemet skapar en dragsession, fångar objektets data och visar drag preview — en genomskinlig kopia av elementet som följer fingret. I denna fas avvisar systemet andra gester (scrollning, textmarkering) tills DnD är slutfört.
Fas 2 — förflyttning (Drag Move): fingret rör sig över skärmen, drag preview följer beröringspunkten. Systemet bestämmer kontinuerligt drop target under fingret och skickar händelserna drag enter, drag move och drag exit. Drop target kan reagera visuellt: lysa, expandera eller visa en insättningslinje. Denna fas varar från 0,5 till 10+ sekunder beroende på uppgiftens komplexitet.
Fas 3 — släpp (Drop): fingret lyfts från skärmen. Systemet avslutar dragsessionen och anropar drop callback vid målelementet. Om drop target avvisar släppet (t.ex. dragning av en fil till en mapp utan skrivrättigheter), återgår drag preview animerat till den ursprungliga positionen (cancel animation). Om släppet accepteras försvinner elementet från den ursprungliga positionen och visas på målpositionen.
| Fas | iOS-händelse | Android-händelse | Visuellt tillstånd |
|---|---|---|---|
| Fångst | UIDragInteractionDelegate.dragSessionWillBegin | View.OnLongClickListener → startDragAndDrop | Drag preview visas under fingret |
| Förflyttning | UIDropInteractionDelegate.dragSessionDidUpdate | View.OnDragListener.onDrag (ACTION_DRAG_MOVED) | Preview rör sig, target lyser |
| Släpp | UIDropInteractionDelegate.performDrop | View.OnDragListener.onDrag (ACTION_DROP) | Animation av släpp eller återgång |
Dragning mellan applikationer — funktion tillgänglig på båda plattformarna. iOS stödjer Drag-and-Drop mellan applikationer i lägena Split View och Slide Over (iPad). Android stödjer dragning mellan applikationer i läget Split Screen. Data överförs via UIPasteConfiguration (iOS) eller ClipData (Android). Utvecklaren anger vilka datatyper som stöds (UTI för iOS, MIME för Android).
UIDragInteraction — det huvudsakliga iOS API:et för dragning, tillagt i iOS 11. För att aktivera dragning från en View, lägg till UIDragInteraction med UIDragInteractionDelegate. Delegerade bestämmer vilka element som dras, deras utseende och beteende. För att ta emot element används UIDropInteraction med UIDropInteractionDelegate, som avgör om View kan acceptera släppet och hur data ska bearbetas.
// UIDragInteraction — dra element från samling
class DragViewController: UIViewController, UIDragInteractionDelegate {
@IBOutlet var dragSourceView: UIView!
override func viewDidLoad() {
super.viewDidLoad()
let dragInteraction = UIDragInteraction(delegate: self)
dragSourceView.addInteraction(dragInteraction)
}
func dragInteraction(_ interaction: UIDragInteraction,
itemsForBeginning session: UIDragSession) -> [UIDragItem] {
guard let data = Data(contentsOf: selectedFileURL) else { return [] }
let itemProvider = NSItemProvider(object: data as NSData)
let dragItem = UIDragItem(itemProvider: itemProvider)
// Drag preview — förminskad kopia av elementet
dragItem.previewProvider = {
let previewView = UIImageView(image: thumbnailImage)
previewView.alpha = 0.8
return UIDragPreview(view: previewView)
}
return [dragItem]
}
}UIDropInteractionDelegate — spegelgränssnittet för att ta emot släpp. Metoden canHandle(_:) kontrollerar om datatypen stöds. sessionDidUpdate(_:) uppdaterar visuellt tillståndet (belysning, insättningslinje). performDrop(_:) utför den slutgiltiga databearbetningen. iOS anropar automatiskt UIDropProposal med operationstypen: .move (flytta), .copy (kopiera), .forbidden (förbjudet). Operationstypen påverkar den visuella visningen (ikon + i hörnet av preview för kopiering, förbudsskylt för forbidden).
View.startDragAndDrop() — Android SDK-metoden för att börja dra, tillgänglig från API 24 (Android 7.0). Anropas efter fångst av elementet (vanligtvis i onLongClick). Parametrar: ClipData (data), DragShadowBuilder (visuell skugga), Object myLocalState (lokalt tillstånd), flags. DragShadowBuilder skapar en Bitmap som följer fingret. Systemet hanterar automatiskt animation och beröringshändelser under dragningen.
// Drag-and-Drop av RecyclerView-element med omordning
class ReorderAdapter(private val items: MutableList<String>) :
RecyclerView.Adapter<ReorderAdapter.ViewHolder>() {
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
holder.itemView.setOnLongClickListener {
// Skapar ClipData för dataöverföring
val clipData = ClipData.newPlainText("item", items[position])
// Anpassad DragShadowBuilder med förminskad preview
val shadowBuilder = object : View.DragShadowBuilder(holder.itemView) {
override fun onProvideShadowMetrics(shadowSize: Point, shadowTouchPoint: Point) {
shadowSize.set(itemView.width, itemView.height / 2)
}
}
holder.itemView.startDragAndDrop(clipData, shadowBuilder, position, 0)
true
}
}
}Ta emot släpp i Android implementeras via View.setOnDragListener(). Lyssnaren tar emot händelserna ACTION_DRAG_STARTED, ACTION_DRAG_ENTERED, ACTION_DRAG_LOCATION, ACTION_DRAG_EXITED, ACTION_DROP, ACTION_DRAG_ENDED. I händelsen ACTION_DROP extraheras data från ClipData och målåtgärden utförs. För RecyclerView med omordning rekommenderas ItemTouchHelper.SimpleCallback — en inbyggd mekanism som automatiskt hanterar Long Press för fångst, förflyttningsanimation av element och hjälpmetoderna onMove/onSwiped.
Omordning av listor (drag to reorder) — det vanligaste DnD-scenariot: användaren drar listelement för att ändra deras ordning. Exempel: omarrangering av kontakter i favoriter, sortering av uppgifter i trackers (Trello, Todoist), ändring av ordningen på låtar i spellistan (Spotify, Apple Music). Implementeras via ItemTouchHelper i Android eller UILongPressGestureRecognizer + omarrangering av celler i iOS.
Filhanterare — Drag-and-Drop för att kopiera och flytta filer mellan mappar. iOS Files App, Android Files by Google, Dropbox — alla stödjer DnD. Att dra en fil till en mapp flyttar den inuti (move), att dra med nedtryckt Option/Ctrl-tangent kopierar den (copy). Drop target lyser visuellt när det närmar sig och visar mappens gränser.
Kanban-tavlor — Trello, Jira, Notion använder Drag-and-Drop för att flytta kort mellan kolumner (To Do → In Progress → Done). Under dragningen lossnar kortet från källkolumnen, följer fingret och vid korsning av gränsen till en annan kolumn infogas det med animation. iOS 11+ stödjer UIDragPreview med parallaxeffekt, där preview avviker något från beröringspunkten, vilket skapar djup.
Springboard-sektioner (iOS) — dragning av appikoner på iOS startskärm. Lång tryckning på en ikon aktiverar „jiggling”-läge (ikonerna skakar), varefter användaren kan flytta ikoner mellan sidor och skapa mappar. Detta är ett av de mest komplexa DnD UX-mönstren eftersom det kräver samtidig hantering av dragning, skakanimation och gruppering i mappar.
Visuell återkoppling — kritisk för Drag-and-Drop. Det dragna objektet bör förändras: bli mindre (iOS: scale 0.8–0.9), bli genomskinligt (alpha 0.7–0.8) och höja sig över gränssnittet med skugga (shadow offset). Drop target bör reagera visuellt vid närmande: lysa (highlight), expandera (expand) eller visa kanter (border). Utan dessa signaler förstår användaren inte var objektet kan släppas.
Återgångsanimation (drag cancel) — om användaren släpper elementet utanför släppzonen eller över en ogiltig zon, bör objektet återgå animerat till den ursprungliga positionen. iOS UIDragInteractionDelegate tillhandahåller dragInteraction(_:sessionDidMove:) för spårning och dragInteraction(_:session:willEndWith:) för återgångsanimation. Android View.setOnDragListener tar emot ACTION_DRAG_ENDED, där återgångsanimationen kan startas via ValueAnimator eller ObjectAnimator.
| Rekommendation | iOS | Android |
|---|---|---|
| Fångst med gest | Long Press (standard) | OnLongClickListener |
| Drag preview | UIDragItem.previewProvider | DragShadowBuilder |
| Taktil återkoppling | UIImpactFeedbackGenerator | HapticFeedbackConstants.LONG_PRESS |
| Återgångsanimation | UIDragPreviewTarget | ViewPropertyAnimator |
| Drop proposal | UIDropProposal (.move/.copy) | ACTION_DROP + flaggor |
| Appar mellan DnD | iOS 11+ Split View (iPad) | Android 7.0+ Split Screen |
Tillgänglighet: användare med motoriska begränsningar kan kanske inte utföra draggesten. Erbjud alternativ via knapparna “Flytta upp/ner” för listor, snabbmenyn “Flytta till mapp” för filer. iOS VoiceOver stödjer rotoråtgärden “Drag” för att flytta element. Android TalkBack erbjuder anpassade åtgärder via AccessibilityNodeInfo.addAction(). Nike Run Club och Apple Health använder DnD för omordning av mätvärden på instrumentpanelen — med åtkomst via standardknappar.
Vanliga frågor
Standardgesten för att starta Drag-and-Drop är Long Press (lång tryckning) som varar 300–500 ms. iOS använder den inbyggda mekanismen UIDragInteraction som automatiskt omvandlar lång beröring till fångst. Android kräver explicit anrop av startDragAndDrop() i OnLongClickListener-callbacken. I vissa fall (t.ex. i spel) kan DnD börja med en enkel beröring utan fördröjning.
Ja, Drag-and-Drop mellan applikationer stöds i iOS 11+ (iPad) och Android 7.0+. På iPad fungerar dragning i lägena Split View och Slide Over — användaren kan ta text från Safari och flytta den till Anteckningar. I Android fungerar DnD mellan appar i Split Screen. Data överförs via UIPasteConfiguration (iOS) eller ClipData (Android) med specifikation av vilka typer som stöds (UTI, MIME).
Konflikten mellan DnD och Scroll löses genom en fördröjning av fångsten. Om användaren börjar röra fingret innan Long Press-timeouten (500 ms) har löpt ut, tolkas gesten som scrollning, inte Drag-and-Drop. I iOS hanterar UIDragInteraction automatiskt denna konflikt via cancelsTouchesInView. I Android använder ItemTouchHelper ett tröskelvärde — om rörelsen överskrider TouchSlop-tröskeln, avbryts Long Press till förmån för scrollning.
Drag-and-Drop stödjer alla datatyper: text, bilder, filer, URL:er, anpassade objekt. iOS använder NSItemProvider med UTI-typer (public.text, public.image, public.file-url). Android — ClipData med MIME-typer (text/plain, image/png, application/octet-stream). För anpassad data skapas ClipData.Item med Intent. Vid DnD mellan appar paketeras data i universella format: plain text, HTML, RTF, UIImage/PNG.
I iOS hanteras återgångsanimationen via UIDragPreviewTarget — den slutliga positionen dit preview återgår animerat. I Android använder du ViewPropertyAnimator med translateX/translateY för att återföra elementet till den ursprungliga positionen. Animationstid — 200–300 ms med en easing-kurva (EaseOut). UIKit lägger automatiskt till UIDragPreview med parallaxeffekt som smidigt återgår när gesten avbryts.
Sammanfattning
Vi utvecklar en mobil applikation nyckelfärdigt
IT Sectr skapar iOS- och Android-applikationer för startups och företag sedan 2017. Vi ger dig råd och föreslår den bästa lösningen.
Läs också