🍎 iOS/UI

[🧩 Creative Coding] 쀄에 맀달렀 ν”λ“€λ¦¬λŠ” μƒμž λ§Œλ“€κΈ° (feat. Interactive Developer)

Fomagran πŸ’» 2021. 11. 23. 23:12
728x90
λ°˜μ‘ν˜•

μ•ˆλ…•ν•˜μ„Έμš” Foma πŸ’» μž…λ‹ˆλ‹€!

 

μ˜€λŠ˜μ€ 쀄에 맀달렀 ν”λ“€λ¦¬λŠ” μƒμžλ₯Ό λ§Œλ“€μ–΄ λ³Όκ±΄λ°μš”.

 

이건 μ œκ°€ μ‘΄κ²½ν•˜λŠ” κ°œλ°œμžμ΄κΈ°λ„ ν•œ μΈν„°λž™ν‹°λΈŒ λ””λ²¨λ‘œνΌ κΉ€μ’…λ―Όλ‹˜μ˜ 유튜브 채널에 올라온 νŠœν† λ¦¬μ–Ό 쀑 ν•˜λ‚˜μΈλ°μš”.

 

μ˜ˆμ „λΆ€ν„° 이런 창의적인 μ½”λ”©, 예술적인 코딩을 ν•˜κ³ μ‹Άμ€ μš•μ‹¬μ΄ λ§Žμ•˜μ—ˆλŠ”λ° 이번 κΈ°νšŒμ— κΉ€μ’…λ―Όλ‹˜μ„ λ”°λΌμ„œ κ΅¬ν˜„ν•΄λ³΄λ €κ³  ν•©λ‹ˆλ‹€.

 

 

μœ„ μ˜μƒμ„ 보며 λ‚˜λ¦„ 제 λ°©μ‹λŒ€λ‘œ Swiftλ₯Ό μ‚¬μš©ν•΄μ„œ κ΅¬ν˜„ν•΄λ³΄μ•˜μŠ΅λ‹ˆλ‹€.

 

λ°”λ‘œ μ‹œμž‘ν• κ²Œμš”~


View

 

λ¨Όμ € μƒμžμ™€ λΉ¨κ°„ 점을 UIView둜 μ„ΈνŒ…ν•΄μ€λ‹ˆλ‹€.

 

(μ €λŠ” μƒμž κ°€μš΄λ°μ— 제 이름을 λ„£μ–΄μ„œ 보여쀄 κ±°κΈ° λ•Œλ¬Έμ— label도 λ„£μ—ˆμŠ΅λ‹ˆλ‹€.)

 

 let square:UIView = {
        let view:UIView = UIView()
        view.backgroundColor = .systemCyan
        return view
    }()
    
    let redDot1:UIView = {
        let view:UIView = UIView()
        view.backgroundColor = .clear
        return view
    }()
    
    let redDot2:UIView = {
        let view:UIView = UIView()
        view.backgroundColor = .clear
        return view
    }()
    
    let label:UILabel = {
        let label:UILabel = UILabel()
        label.text = "Fomagran"
        label.font = .systemFont(ofSize: 18, weight: .bold)
        label.textColor = .white
        return label
    }()

1. μƒμž 움직이기

 

μƒμžλ₯Ό ν„°μΉ˜ν•΄μ„œ μ›€μ§μ΄κ²Œ ν•˜λ €λ©΄ μ–΄λ–»κ²Œ ν•΄μ•Όν• κΉŒμš”?

 

λ°”λ‘œ νŒ¬μ œμŠ€μ³λΌλŠ” 것을 μ΄μš©ν•΄μ£Όμ–΄μ•Ό ν•©λ‹ˆλ‹€.

 

μƒμžμ— μ•„λž˜μ™€ 같이 팬제슀쳐λ₯Ό λ‹¬μ•„μ€λ‹ˆλ‹€.

 

private func setPanGesture() {
        let panGesture = UIPanGestureRecognizer(target: self, action: #selector(self.dragSquare(_:)))
        square.addGestureRecognizer(panGesture)
    }

 

μƒμžλ₯Ό λ“œλž˜κ·Έ ν–ˆμ„ λ•Œ μ•„λž˜μ™€ 같이 μ‹€ν–‰μ‹œμΌœμ£Όλ©΄ 

 

    @objc func dragSquare(_ sender: UIPanGestureRecognizer) {
        let transition = sender.translation(in: square)
        let newX = square.center.x + transition.x
        let newY = square.center.y + transition.y
        square.center = CGPoint(x: newX, y: newY)
        sender.setTranslation(CGPoint.zero, in: square)
    }

 

μƒμžλ₯Ό 움직일 수 있게 λ©λ‹ˆλ‹€.

 


2. μƒμžλ₯Ό ν„°μΉ˜ν•œ λΆ€λΆ„ λΉ¨κ°„ 점으둜 ν‘œμ‹œν•˜κΈ°

 

μœ„ μ˜μƒμ„ 보면 μƒμžλ₯Ό ν„°μΉ˜ν•œ 뢀뢄에 λΉ¨κ°„ 점이 생기고 선이 μƒκ²¨μ„œ 맀달렀 움직이죠?

 

κ·Έλ ‡λ‹€λ©΄ μ–΄λ–»κ²Œ μƒμžλ₯Ό κ°€μž₯ μ²˜μŒμ— ν„°μΉ˜ν•œ 뢀뢄을 μ•Œμ•„λ‚Ό 수 μžˆμ„κΉŒμš”?

 

λ°”λ‘œ 처음 λ“œλž˜κ·Έλ₯Ό μ‹œμž‘ν•  λ•Œ μœ„μΉ˜λ₯Ό μ•Œμ•„λ‚΄λ©΄ λ©λ‹ˆλ‹€.

 

UIPanGestureRecognizerλ₯Ό μ΄μš©ν•΄μ„œ λ“œλž˜κ·Έκ°€ μ‹œμž‘λ  λ•Œ μœ„μΉ˜λ₯Ό μ•Œμ•„λƒ…λ‹ˆλ‹€.

 

그리곀 빨간점1의 색을 λΉ¨κ°„μƒ‰μœΌλ‘œ λ°”κΏ”μ€λ‹ˆλ‹€.

 

 @objc func dragSquare(_ sender: UIPanGestureRecognizer) {
        if sender.state == .began {
            let location = sender.location(in: view) //λ“œλž˜κ·Έλ₯Ό μ‹œμž‘ν•œ μœ„μΉ˜
            redDot1.center = location
            redDot1.backgroundColor = .red
            ...

 

μ΄λ ‡κ²Œ ν•˜λ©΄ μ•„λž˜μ™€ 같이 λ“œλž˜κ·Έλ₯Ό μ‹œμž‘ν•  λ•Œ 지점이 λΉ¨κ°„μƒ‰μœΌλ‘œ ν‘œμ‹œλ©λ‹ˆλ‹€.

 

 


2. 두 번째 빨간점 λ“œλž˜κ·Έ μœ„μΉ˜μ— ν‘œμ‹œν•˜κΈ°

 

μƒμžλ₯Ό ν„°μΉ˜ν•œ 뢀뢄에 λΉ¨κ°„ 점을 ν‘œμ‹œν–ˆλ‹€λ©΄ λ“œλž˜κ·Έλ₯Ό ν•˜λŠ” μœ„μΉ˜μ— 따라 ν‘œμ‹œλ˜λŠ” λΉ¨κ°„ 점도 λ³΄μ—¬μ€˜μ•Όκ² μ£ ?

 

λ“œλž˜κ·Έκ°€ λ°”λ€” λ•Œμ˜ μœ„μΉ˜λ₯Ό μ•Œμ•„λ‚΄μ–΄ 빨간점2의 μœ„μΉ˜λ₯Ό λ°”κΏ”μ€λ‹ˆλ‹€.

 

 @objc func dragSquare(_ sender: UIPanGestureRecognizer) {
        if sender.state == .began {
            let location = sender.location(in: view) //λ“œλž˜κ·Έλ₯Ό μ‹œμž‘ν•œ μœ„μΉ˜
            redDot1.center = location
            redDot1.backgroundColor = .red
          }else if sender.state == .changed {
            redDot2.center = sender.location(in: view)
            redDot2.backgroundColor = .red
            ...

 

그럼 μ•„λž˜μ™€ 같이 λ“œλž˜κ·Έλ₯Ό ν•˜λ©΄ 처음 μœ„μΉ˜μ™€ λ“œλž˜κ·Έλ₯Ό ν•˜λŠ” μœ„μΉ˜μ— 따라 빨간점 두 κ°œκ°€ ν‘œμ‹œλ©λ‹ˆλ‹€.

 


3. λΉ¨κ°„ 점 두 개 μ„ μœΌλ‘œ μž‡κΈ°

 

이제 λΉ¨κ°„ 점 두 개λ₯Ό μ„ μœΌλ‘œ μ΄μ–΄μ€˜μ•Όκ² μ£ ?

 

선을 λ§Œλ“€μ–΄ μ£ΌκΈ° μœ„ν•΄μ„  CAShapeLayer둜 λ§Œλ“€μ–΄μ€˜μ•Ό ν•©λ‹ˆλ‹€.

 

private var line = CAShapeLayer()

 

μ•„λž˜μ™€ 같이 μ‹œμž‘κ³Ό 끝을 지정해주고 μ„ μœΌλ‘œ μ΄μ–΄μ€λ‹ˆλ‹€.

 

 private func addLine(start: CGPoint,end:CGPoint) {
        line.removeFromSuperlayer()
        let linePath = UIBezierPath()
        linePath.move(to: start)
        linePath.addLine(to: end)
        line.path = linePath.cgPath
        line.strokeColor = UIColor.red.cgColor
        line.lineWidth = 1
        view.layer.addSublayer(line)
    }

 

빨간점1κ³Ό 빨간점2의 쀑앙 뢀뢄을 μ„ μœΌλ‘œ μ΄μ–΄μ€λ‹ˆλ‹€.

 

 @objc func dragSquare(_ sender: UIPanGestureRecognizer) {
        if sender.state == .began {
            let location = sender.location(in: view) //λ“œλž˜κ·Έλ₯Ό μ‹œμž‘ν•œ μœ„μΉ˜
            redDot1.center = location
            redDot1.backgroundColor = .red
          }else if sender.state == .changed {
            redDot2.center = sender.location(in: view)
            redDot2.backgroundColor = .red
            addLine(start: redDot1.center,end:redDot2.center)
            ...

 

μ•„λž˜μ™€ 같이 μ„ μœΌλ‘œ 두 개의 점이 μ΄μ–΄μ§‘λ‹ˆλ‹€.

 


4. λ“œλž˜κ·Έκ°€ λλ‚˜λ©΄ μ„ κ³Ό 점 μ‚¬λΌμ§€κ²Œ ν•˜κΈ°

 

λ“œλž˜κ·Έκ°€ λλ‚˜λŠ” μˆœκ°„μ—λŠ” μ„ κ³Ό 점이 사라져야겠죠?

 

빨간점 두 κ°œμ™€ μ„ μ˜ 색을 λ°”κΏ”μ£ΌλŠ” λ©”μ„œλ“œλ₯Ό κ΅¬ν˜„ν•΄μ€λ‹ˆλ‹€.

 

 private func changeColor(_ color:UIColor) {
        redDot1.backgroundColor = color
        redDot2.backgroundColor = color
        line.strokeColor = color.cgColor
    }

 

dragSquare λ©”μ†Œλ“œμ— λ“œλž˜κ·Έκ°€ 끝났을 λ•Œ 색을 투λͺ…μƒ‰μœΌλ‘œ λ°”κΏ”μ€λ‹ˆλ‹€.

 

 @objc func dragSquare(_ sender: UIPanGestureRecognizer) {
	...
    
    }else if sender.state == .ended {
            changeColor(.clear)
            ...

 

 


5. νŠΉμ • 길이 이상 λŠ˜μ–΄λ‚˜λ©΄ 빨간점1 움직이기

 

선을 μž‘μ•„λ‹ΉκΈ°λ‹€κ°€ νŠΉμ • 길이 이상 λŠ˜μ–΄λ‚˜λ©΄ 빨간점 1을 μ›€μ§μ΄κ²Œ λ§Œλ“€μ–΄ μ€„κ±΄λ°μš”.

 

λ¨Όμ € 두 개의 점의 길이λ₯Ό μ•Œμ•„λ‚΄μ•Όκ² μ£ ?

μ•„λž˜μ™€ 같이 두 개의 점의 길이λ₯Ό μ•Œμ•„λƒ…λ‹ˆλ‹€.

 

 private func getTwoPointDistance(_ point1:CGPoint,_ point2:CGPoint) -> CGFloat {
        let xDist:CGFloat = point2.x - point1.x
        let yDist:CGFloat = point2.y - point1.y
        return sqrt((xDist * xDist) + (yDist * yDist))
    }

 

dragSquare λ©”μ„œλ“œμ—μ„œ λ“œλž˜κ·Έκ°€ λ³€ν•  λ•Œμ— μ•„λž˜μ™€ 같이 두 개의 점의 길이λ₯Ό μ•Œμ•„λ‚Έ λ’€

 

νŠΉμ • 길이 이상 λŠ˜μ–΄λ‚˜λ©΄ 빨간점2의 μœ„μΉ˜λ‘œ 빨간점1의 μœ„μΉ˜λ₯Ό λ³€κ²½ν•˜κ² μŠ΅λ‹ˆλ‹€.

 

        }else if sender.state == .changed {
            redDot2.center = sender.location(in: view)
            redDot2.backgroundColor = .red
            addLine(start: redDot1.center,end:redDot2.center)
            let distance:CGFloat = getTwoPointDistance(redDot1.center,redDot2.center)
            if distance > 100 {
                redDot1.center = redDot2.center
            }

 

μ•„λž˜μ™€ 같이 보면 μƒμžκ°€ μ›€μ§μ΄λŠ”κ²Œ 맀우 μ–΄μƒ‰ν•˜μ£ ?

 

UIView.animateλ₯Ό μ‚¬μš©ν•˜λ©΄ μ›€μ§μž„μ„ 훨씬 λΆ€λ“œλŸ½κ²Œ λ°”κΏ€ 수 μžˆμŠ΅λ‹ˆλ‹€.

 

  if distance > 100 {
                UIView.animate(withDuration: 0.5) {
                    self.redDot1.center = self.redDot2.center
                }

 

 


6. μ„  λŠκΉ€ ν˜„μƒ ν•΄κ²°ν•˜κΈ°

 

ν•˜μ§€λ§Œ μœ„μ—μ„œ μ• λ‹ˆλ©”μ΄μ…˜μ„ μ μš©ν–ˆμ„ λ•Œ λΆ€λ“œλŸ¬μ›Œμ§€κΈ΄ ν•˜μ§€λ§Œ 빨간점1이 이동 쀑에 잠깐 선이 λŠκΈ°λŠ” ν˜„μƒμ΄ λ°œμƒν–ˆμŠ΅λ‹ˆλ‹€.

 

κ·Έ μ΄μœ λŠ” μ• λ‹ˆλ©”μ΄μ…˜ μ μš©ν•˜λ©΄ λ°”λ€ŒλŠ” 값에 따라 선이 μ—°κ²°λ˜μ§€ μ•ŠκΈ° λ•Œλ¬Έμž…λ‹ˆλ‹€.

 

μ• λ‹ˆλ©”μ΄μ…˜μ΄ λ°”λ€ŒλŠ” 값에 따라 선을 μ—°κ²°ν•˜λ €λ©΄ μ–΄λ–»κ²Œ ν•΄μ•Όν• κΉŒμš”?

 

λ°”λ‘œ CADisplayLinkλ₯Ό μ‚¬μš©ν•΄μ£Όλ©΄ λ©λ‹ˆλ‹€.

 

CADisplayLinkλŠ” 화면이 μ—…λ°μ΄νŠΈ 될 λ•Œλ§ˆλ‹€ ν˜ΈμΆœλ˜λŠ” NSObjectμΈλ°μš”.

 

 

μ•„λž˜μ™€ 같이 μ„ μ–Έν•΄μ£Όμ‹œκ³  

 

var displayLink:CADisplayLink?

 

λ””μŠ€ν”Œλ ˆμ΄λ§ν¬λ₯Ό 생성해 μ£ΌλŠ” λ©”μ„œλ“œλ₯Ό κ΅¬ν˜„ν•΄μ€λ‹ˆλ‹€.

 

private func createDisplayLink() {
        let displaylink = CADisplayLink(target: self,selector: #selector(displayLinkLoop))
        displaylink.add(to: .current,forMode:.common)
        displayLink = displaylink
    }

 

그리고 μ• λ‹ˆλ©”μ΄μ…˜μ΄ μ‹€ν–‰λ˜κΈ° 직전에 λ””μŠ€ν”Œλ ˆμ΄ 링크λ₯Ό 생성해 μ€λ‹ˆλ‹€.

 

          if distance > 100 {
                createDisplayLink()
                UIView.animate(withDuration: 0.5) {
                    self.redDot1.center = self.redDot2.center
                }

 

그리고 λ””μŠ€ν”Œλ ˆμ΄λ§ν¬λ₯Ό 좜λ ₯해보면 

 

@objc func displayLinkLoop(displaylink: CADisplayLink) {
        print(displaylink)

 

화면이 μ—…λ°μ΄νŠΈ 될 λ•Œλ§ˆλ‹€ μ•„λž˜μ™€ 같이 λ””μŠ€ν”Œλ ˆμ΄ 링크가 ν˜ΈμΆœλ©λ‹ˆλ‹€.

 

 

 

이것을 μ΄μš©ν•΄μ„œ μ• λ‹ˆλ©”μ΄μ…˜μ„ μ‚¬μš©ν•˜μ§€ μ•Šκ³  λΆ€λ“œλŸ½κ²Œ 빨간점1을 μ΄λ™μ‹œν‚€κ² μŠ΅λ‹ˆλ‹€.

 

빨간점2의 μœ„μΉ˜λ₯Ό κΈ°μ–΅ν•  goal을 λ§Œλ“€μ–΄μ€λ‹ˆλ‹€.

 

var goal = CGPoint()

 

μ•„λž˜μ™€ 같이 λ””μŠ€ν”Œλ ˆμ΄λ§ν¬λ₯Ό μƒμ„±ν•˜κΈ° 직전에 goal의 μœ„μΉ˜λ₯Ό 빨간점2의 μ€‘μ•™μœΌλ‘œ μ„ΈνŒ…ν•©λ‹ˆλ‹€.

 

 if distance > 100 {
                goal = redDot2.center
                createDisplayLink()
            }

 

그리고 λ””μŠ€ν”Œλ ˆμ΄ 링크λ₯Ό ν˜ΈμΆœν•˜λŠ” λ©”μ„œλ“œμ— μ•„λž˜μ™€ 같이 goal의 μœ„μΉ˜κ°€ 될 λ•ŒκΉŒμ§€ μ„ μœΌλ‘œ μ—°κ²°ν•΄μ€λ‹ˆλ‹€.

 

    @objc func displayLinkLoop(displaylink: CADisplayLink) {
        if round(redDot1.center.x) == round(goal.x) && round(redDot1.center.y) == round(goal.y){
            displaylink.invalidate()
            line.strokeColor = UIColor.clear.cgColor
            return
        }
        if round(redDot1.center.x) != round(goal.x) {
            redDot1.center.x += redDot1.center.x < goal.x ? 1: -1
        }

        if round(redDot1.center.y) != round(goal.y) {
            redDot1.center.y += redDot1.center.y < goal.y ? 1 : -1
        }
        
        addLine(start: redDot1.center,end: redDot2.center)
    }
}

 

그럼 μ•„λž˜μ™€ 같이 μ• λ‹ˆλ©”μ΄μ…˜μ„ μ΄μš©ν•˜μ§€ μ•Šκ³  λΉ¨κ°„ 점1의 μœ„μΉ˜λ₯Ό λΆ€λ“œλŸ½κ²Œ μ΄λ™μ‹œν‚¬ 수 μžˆμŠ΅λ‹ˆλ‹€.

 


7. 빨간점1의 μœ„μΉ˜μ— 따라 μƒμž 움직이기

 

이제 빨간점1의 μœ„μΉ˜μ— λ”°λΌμ„œ μƒμžλ₯Ό μ›€μ§μ—¬λ³΄λŠ” 것을 κ΅¬ν˜„ν•˜κ² μŠ΅λ‹ˆλ‹€.

 

빨간점1의 μœ„μΉ˜λŠ” 맨 처음 λ“œλž˜κ·Έκ°€ μ‹œμž‘λœ 곳의 μœ„μΉ˜μ£ ?

 

고둜 빨간점1의 쀑앙과 μƒμžμ˜ μ€‘μ•™μ˜ 차이λ₯Ό 계산해야 ν•©λ‹ˆλ‹€.

 

빨간점1κ³Ό μƒμžμ˜ 차이λ₯Ό 기둝할 gap을 λ§Œλ“€μ–΄μ€λ‹ˆλ‹€.

 

private var gap:CGPoint = CGPoint()

 

그리고 λ“œλž˜κ·Έκ°€ μ‹œμž‘λ  λ•Œ μƒμžμ™€ λΉ¨κ°„ 점의 μœ„μΉ˜λ₯Ό κ³„μ‚°ν•΄μ„œ gap에 μ €μž₯ν•΄μ€λ‹ˆλ‹€.

 

 if sender.state == .began {
            let location = sender.location(in: view)
            gap.x = square.center.x - location.x
            gap.y = square.center.y - location.y

 

κ·Έ λ‹€μŒ λ””μŠ€ν”Œλ ˆμ΄ 링크가 호좜될 λ•Œ μƒμžμ˜ μœ„μΉ˜λ₯Ό 차이만큼 더해쀀 κ°’μœΌλ‘œ μ§€μ •ν•΄μ€λ‹ˆλ‹€.

 

    @objc func displayLinkLoop(displaylink: CADisplayLink) {
        if round(redDot1.center.x) == round(goal.x) && round(redDot1.center.y) == round(goal.y){
            displaylink.invalidate()
            line.strokeColor = UIColor.clear.cgColor
            return
        }
        if round(redDot1.center.x) != round(goal.x) {
            redDot1.center.x += redDot1.center.x < goal.x ? 1: -1
            square.center.x = redDot1.center.x + gap.x
        }

        if round(redDot1.center.y) != round(goal.y) {
            redDot1.center.y += redDot1.center.y < goal.y ? 1 : -1
            square.center.y = redDot1.center.y + gap.y
        }
        
        addLine(start: redDot1.center,end: redDot2.center)
    }

 

μ•„λž˜μ™€ 같이 빨간점1의 μœ„μΉ˜μ— 따라 μƒμžκ°€ μ›€μ§μ΄κ²Œ λ©λ‹ˆλ‹€.

 


8. 빨간점1κ³Ό 빨간점2의 거리두기(μ˜΅μ…”λ„)

 

빨간점1이 빨간점2의 μœ„μΉ˜λ‘œ κ°€λŠ” 것이 μ•„λ‹Œ κ·Έ 근처둜 κ°€κ²Œλ” κ΅¬ν˜„ν•˜κ³  μ‹Άμ—ˆλŠ”λ°μš”.

 

(이건 ν•˜μ…”λ„ 되고 μ•ˆν•˜μ…”λ„ λ©λ‹ˆλ‹€.)

 

μ΄λ ‡κ²Œ μ„€λͺ…ν•˜λ©΄ 이해가 μ•ˆλ˜λ‹ˆ μ™Όμͺ½μ€ 빨간점2의 μ’Œν‘œκΉŒμ§€ μ΄λ™ν•˜λŠ” 것이고 였λ₯Έμͺ½μ€ 빨간점2의 κ·Όμ²˜κΉŒμ§€λ§Œ μ΄λ™ν•˜λŠ” κ²ƒμž…λ‹ˆλ‹€.

 

 

μƒμžμ˜ 쀑앙을 κΈ°μ€€μœΌλ‘œ x,y의 μŒμˆ˜μ™€ μ–‘μˆ˜μ— 따라 λ²”μœ„λ₯Ό λ‚˜λˆ„κ³  빨간점2의 μœ„μΉ˜μ— 따라 빨간점1의 μœ„μΉ˜λ₯Ό

 

κ΅¬ν•΄μ£Όμ—ˆμŠ΅λ‹ˆλ‹€.

 

 

μ•„λž˜μ™€ 같이 λ²”μœ„μ— 따라 ꡬ할 수 μžˆμŠ΅λ‹ˆλ‹€.

 

  func getDestinationPoint(p2:CGPoint) -> CGPoint {
        if p2.x <= center.x  {
            //1
            if p2.y <= center.y {
                return CGPoint(x: p2.x+50, y: p2.y+50)
            //3
            }else {
                return CGPoint(x: p2.x+50, y: p2.y-50)
            }
        }else {
            //2
            if p2.y <= center.y {
                return CGPoint(x: p2.x-50, y: p2.y+50)
            //4
            }else {
                return CGPoint(x: p2.x-50, y: p2.y-50)
            }
        }
    }

 

goal의 μœ„μΉ˜λ₯Ό μ•„λž˜μ™€ 같이 μ„€μ •ν•΄μ€λ‹ˆλ‹€.

 

  if distance > 100 {
                goal = square.getDestinationPoint(p2: redDot2.center)
                createDisplayLink()
            }

9. μƒμž νšŒμ „ν•˜κΈ°

 

쀄을 당겨 μƒμžλ₯Ό 움직일 λ•Œ λ°©ν–₯에 따라 μƒμžκ°€ μ•½κ°„μ”© νšŒμ „λ˜λŠ” 것을 λ³Ό 수 μžˆμŠ΅λ‹ˆλ‹€.

 

이것 λ˜ν•œ μœ„μ²˜λŸΌ λ²”μœ„λ₯Ό λ‚˜λˆ  빨간점 2의 μœ„μΉ˜μ— 따라 μ–΄λŠ λ°©ν–₯인지 μ•Œμ•„λ‚Ό 수 μžˆμ—ˆμŠ΅λ‹ˆλ‹€.

 

λ²”μœ„μ— 따라 μ•„λž˜μ™€ 같이 νšŒμ „κ°’μ„ μ§€μ •ν•΄μ£Όμ—ˆμŠ΅λ‹ˆλ‹€.

 

(5둜 μ§€μ •ν–ˆμ§€λ§Œ μ›ν•˜μ‹œλŠ” νšŒμ „κ°’μ„ λ„£μœΌμ‹œλ©΄ λ©λ‹ˆλ‹€.)

 

 func getAngle(p2:CGPoint) -> CGFloat {
        if p2.x <= center.x  {
            //1
            if p2.y <= center.y {
                return 5
            //3
            }else {
                return -5
            }
        }else {
            //2
            if p2.y <= center.y {
                return -5
            //4
            }else {
                return 5
            }
        }
    }

 

그리고 λ·°λ₯Ό νšŒμ „ν•  수 μžˆλŠ” λ©”μ„œλ“œλ₯Ό λ§Œλ“€μ–΄μ£Όμ—ˆμŠ΅λ‹ˆλ‹€.

 

func rotate(degrees: CGFloat) {
        let degreesToRadians: (CGFloat) -> CGFloat = { (degrees: CGFloat) in
            return degrees / 180.0 * CGFloat.pi
        }
        self.transform =  CGAffineTransform(rotationAngle: degreesToRadians(degrees))
    }

 

μ•„λž˜μ™€ 같이 λ“œλž˜κ·Έ 값이 λ°”λ€” λ•Œ 빨간점2의 μœ„μΉ˜μ— 따라 각도λ₯Ό ꡬ해 νšŒμ „ν•˜κ³ 

 

λ“œλž˜κ·Έκ°€ 끝날 λ•Œ νšŒμ „μ„ 0λ„λ‘œ λ§Œλ“€μ–΄ 제자리둜 λŒμ•„μ˜€κ²Œ κ΅¬ν˜„ν•˜μ˜€μŠ΅λ‹ˆλ‹€.

 

@objc func dragSquare(_ sender: UIPanGestureRecognizer) {
        if sender.state == .began {
            let location = sender.location(in: view)
            gap.x = square.center.x - location.x
            gap.y = square.center.y - location.y
            changeColor(.red)
            redDot1.center = location
        }else if sender.state == .changed {
            redDot2.center = sender.location(in: view)
            addLine(start: redDot1.center,end:redDot2.center)
            let distance:CGFloat = getTwoPointDistance(redDot1.center,redDot2.center)
            if distance > 100 {
                goal = square.getDestinationPoint(p2: redDot2.center)
                createDisplayLink()
                let angle:CGFloat = square.getAngle(p2:redDot2.center)
                rotateAndChangeColor(angle: angle, color: .systemRed)
            }
        }else if sender.state == .ended {
            changeColor(.clear)
            rotateAndChangeColor(angle: 0, color: .clear)
        }
    }

 

νšŒμ „κ³Ό 색을 바꿔쀄 λ•Œ μ• λ‹ˆλ©”μ΄μ…˜μ„ μ€˜μ„œ λΆ€λ“œλŸ½κ²Œ λ§Œλ“€μ–΄ μ£Όμ—ˆμŠ΅λ‹ˆλ‹€.

 

private func rotateAndChangeColor(angle:CGFloat,color:UIColor) {
        UIView.animate(withDuration: 0.5) {
            self.square.rotate(degrees:angle)
            self.label.rotate(degrees:angle)
            self.changeColor(color)
        }
    }

 

μ•„λž˜μ™€ 같이 쀄을 λ‹ΉκΈ°λŠ” λ°©ν–₯에 따라 μƒμžκ°€ νšŒμ „ν•˜λŠ” 것을 λ³Ό 수 μžˆμŠ΅λ‹ˆλ‹€.

 


μ˜€λŠ˜μ€ μ΄λ ‡κ²Œ μΈν„°λž™ν‹°λΈŒ λ””λ²¨λ‘œνΌλ‹˜μ˜ νŠœν† λ¦¬μ–Όμ„ κ΅¬ν˜„ν•΄λ³΄μ•˜λŠ”λ°μš”.

 

보기엔 정말 κ°„λ‹¨ν•˜λ‹€κ³  μƒκ°ν–ˆλ˜ 것듀이 직접 κ΅¬ν˜„ν•˜λ €κ³  ν•˜λ‹ˆ μ‹œκ°„λ„ 였래 걸리고 κ½€ λ³΅μž‘ν–ˆμŠ΅λ‹ˆλ‹€.

 

이 νŠœν† λ¦¬μ–Όμ„ ν†΅ν•΄μ„œ λ‚˜λ¦„ 배운 것도 많고 μ˜ˆμ „λΆ€ν„° ν•˜κ³ μ‹Άμ—ˆλ˜ ν¬λ¦¬μ—μ΄ν‹°λΈŒ μ½”λ”©μ΄λΌμ„œ κ΅¬ν˜„ν•˜κ³  λ‚˜λ‹ˆ λΏŒλ“―ν•˜λ„€μš”...γ…Žγ…Ž

728x90
λ°˜μ‘ν˜•