2016-03-19 15 views
4

Ich versuche, etwas für einen iOS-App (Swift) neu erstellen, die ich bereits in HTML5 gemacht (mit maparea-coords).anklickbare Körperbildes mit Swift (iOS)

Ich möchte ein Diagramm des menschlichen Körpers zeigen, das mit Klicks/Berührungen des Benutzers interagiert. Der Körper besteht aus beispielsweise 20 verschiedenen Teilen, und der Benutzer kann einen oder mehrere Körperteile auswählen. Für jeden Körperteil gibt es ein ausgewähltes Zustandsbild, das angezeigt werden soll, wenn ein Teil ausgewählt wird. Durch Klicken auf einen ausgewählten Teil wird die Auswahl aufgehoben. Nach der Auswahl eines oder mehrerer Teile kann der Benutzer fortfahren und erhält Informationen über diese Teile in einem nächsten viewcontroller. Ich füge ein vereinfachtes Bild an, um mein Ziel zu erklären.

bodyparts selection

Kann jemand erklären, was der beste Weg, dieses Ziel zu erreichen ist? Gibt es eine vergleichbare Technik, die in Swift verwendet werden kann, um ein solches interaktives Bild zu erstellen?

Danke!

+0

Sie wollen es 2 D oder 3D? – rptwsthi

+0

Ich würde empfehlen ** hitTest: ** und CALayer, hier ist die [äquivalent in ObjC] (http://sketchytech.blogspot.co.uk/2012/10/the-secret-life-of-calayer-part- 2.html) was ich glücklicherweise in Swift übersetzen kann, wenn es nützlich aussieht – sketchyTech

+0

@sketchyTech 'CALayer'' hitTest' funktioniert nur mit den rechteckigen Grenzen einer Ebene. Die Abbildung des OP zeigt unregelmäßige Formen.Ich denke, die Verwendung von Bezier-Pfaden und 'containsPoint' wäre für diesen Fall besser. (Plus-Layer sind eine untergeordnete Systemkomponente, die eine andere Komplexitätsebene einführt.) Sie sind sicherlich leistungsstark, aber ich denke nicht, dass sie diese zusätzliche Komplexität in diesem Fall wert sind. –

Antwort

0

Behoben!

Zuerst habe ich hinzugefügt Subschichten auf die UIImageView wie diese

var path = UIBezierPath() 
path.moveToPoint(CGPointMake(20, 30)) 
path.addLineToPoint(CGPointMake(40, 30)) 

// add as many coordinates you need... 

path.closePath() 

var layer = CAShapeLayer() 
layer.path = path.CGPath 
layer.fillColor = UIColor(red: 255, green: 0, blue: 0, alpha: 0.5).CGColor 
layer.hidden = true 

bodyImage.layer.addSublayer(layer) 

als ich die touchesBegan Funktion, um overrided ein- und ausblenden, wenn die Formen angezapft werden.

override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent?) { 

    if let touch = touches.first! as? UITouch { 
     // get tapped position 
     let position = touch.locationInView(self.bodyImage) 

     // loop all sublayers 
     for layer in self.bodyImage.layer.sublayers! as! [CAShapeLayer] { 

      // check if tapped position is inside shape-path 
      if CGPathContainsPoint(layer.path, nil, position, false) { 
       if (layer.hidden) { 
        layer.hidden = false 
       } 
       else { 
        layer.hidden = true 
       } 
      } 
     } 
    } 
} 
+0

Hallo, ich versuche etwas sehr ähnliches zu machen, aber ich bin irgendwie neu dazu. Könnten Sie möglicherweise einen Beispielcode auf GitHub veröffentlichen, damit ich anfangen kann? Ich verstehe etwas von diesem Code nicht. Danke! – Pangu

+0

@Pangu hast du irgendeine Probe auf diese, ich bin auf der Suche nach etwas Ähnliches zu – srivas

+0

@Duncan C erwähnte das Gleiche ... – Ali

0

Es gibt keinen eingebauten Mechanismus zum Erkennen von Taps in unregelmäßigen Formen. Die standardmäßige UIView-Tap-Erkennung verwendet Rahmenrechtecke. (Gleichfalls mit CALayers, wie von sketchyTech in seinem Kommentar oben vorgeschlagen.)

Ich würde vorschlagen, Ihre Körperregionen als Bezier-Pfade zu zeichnen. Sie könnten eine benutzerdefinierte Unterklasse von UIView (BodyView) erstellen, die ein Array von BodyRegion-Objekten verwaltet, von denen jedes einen Bezier-Pfad enthält.

Die UIBezierPath Klasse enthält eine Methode contains, mit dem Sie feststellen, ob ein Punkt innerhalb des Pfades ist. Ihre BodyView könnte uns das entscheiden, welches Pfadobjekt angezapft wurde.

Bézier-Pfade würden sowohl Ihre Körperregionen als auch abhandeln und herausfinden, welcher Teil angezapft wurde.

+0

hast du irgendein Beispiel dafür, ich suche etwas ähnliches auch – srivas

+0

@srivas, nein, ich habe kein Beispiel. Es ist nicht so kompliziert. Versuchen Sie es mit der Methode 'containsPoint()', die ich beschreibe, und schreiben Sie eine Frage, wenn Sie nicht richtig arbeiten können. –

0

Eine sehr einfache Möglichkeit, dies zu erreichen, wäre unsichtbare Schaltflächen über die Bereiche zu setzen, haken dann ein jeder bis zu einem IBAction und setzen alles, was Sie im Inneren passieren soll.

@IBAction func shinTapped(sender: UIButton) { 
    tappedCounter = 0 
    if tappedCounter == 0 { 
     // set property to keep track 
     shinSelected = true 
     // TODO: set button image to selected state 
     // increment counter 
     tappedCounter++ 
     }else{ 
     // set property to keep track 
     shinSelected = false 
     // TODO: set button image to nil 
     // reset counter 
     tappedCounter = 0 
    } 

Dies könnte ein wenig schwierig zu Layout bekommen, so dass jede Taste an der richtigen Stelle sitzt, aber wenn man mit Größenklassen arbeitet, ist es völlig machbar. Ich bin mir sicher, dass es einen eleganteren Weg gibt, dies zu tun, aber das ist ein Weg.