๋ณธ๋ฌธ ๋ฐ”๋กœ๊ฐ€๊ธฐ
SeSAC

[iOS] TIL_230801

by lizzydev 2023. 8. 3.

ํ”„๋กœํผํ‹ฐ

์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ (ํด๋ž˜์Šค/๊ตฌ์กฐ์ฒด๋ฅผ ์ดˆ๊ธฐํ™”๋ฅผ ํ•ด์•ผ ํ”„๋กœํผํ‹ฐ์— ์ ‘๊ทผ ๊ฐ€๋Šฅ)

์„ ์–ธ๊ณผ ์ดˆ๊ธฐํ™”๋ฅผ ๋™์‹œ์— or ์„ ์–ธ๋งŒ ํ•ด๋‘๊ณ  ์ธ์Šคํ„ด์Šค ์ƒ์„ฑ ์‹œ ์ดˆ๊ธฐํ™” ํ•ด๋„ ๋จ!

struct User {     
	var nickname: String     
	//์„ ์–ธ๊ณผ ์ดˆ๊ธฐํ™”๋ฅผ ๋™์‹œ์— or ์„ ์–ธ๋งŒ ํ•ด๋‘๊ณ  ์ธ์Šคํ„ด์Šค ์ƒ์„ฑ ์‹œ ์ดˆ๊ธฐํ™” ํ•ด๋„ ๋จ!     
	//์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ + ์ €์žฅ ํ”„๋กœํผํ‹ฐ          
	static var originName: String = "์ง„์งœ ์ด๋ฆ„"     
	//ํƒ€์ž… ํ”„๋กœํผํ‹ฐ(Meta Type) + ์ €์žฅ ํ”„๋กœํผํ‹ฐ     
	//์‚ฌ์šฉํ•˜๊ฒŒ ๋˜๋Š” ์ˆœ๊ฐ„ ๋ฉ”๋ชจ๋ฆฌ์— ์˜ฌ๋ผ๊ฐ, ์•ฑ ์ข…๋ฃŒ๊นŒ์ง€ ๋ฉ”๋ชจ๋ฆฌ ์œ ์ง€     
	//์ง€์—ฐ ์ €์žฅ ํ”„๋กœํผํ‹ฐ(lazy) ์ฒ˜๋Ÿผ ๋™์ž‘   
}

์ธ์Šคํ„ด์Šค๋Š” ์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ๋งŒ ์ ‘๊ทผ ๊ฐ€๋Šฅ

ํƒ€์ž… ํ”„๋กœํผํ‹ฐ ์ ‘๊ทผ ๋ถˆ๊ฐ€

ํƒ€์ž…์ด๋ฆ„์œผ๋กœ ์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ ์ ‘๊ทผ๋ถˆ๊ฐ€

ํƒ€์ž… ํ”„๋กœํผํ‹ฐ ์ ‘๊ทผ ๊ฐ€๋Šฅ

  • ์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ ์•„๋ฌด๋ฆฌ ๋งŽ์•„๋„ ํƒ€์ž… ํ”„๋กœํผํ‹ฐ๋Š” ๊ทธ๋Œ€๋กœ์ž„
  • ํ•˜์ง€๋งŒ ํƒ€์ž…ํ”„๋กœํผํ‹ฐ ์ ‘๊ทผํ•ด์„œ ๋ฐ”๊ฟ”์ฃผ๋ฉด ๋ฐ”๋€œ
  • ํƒ€์ž… ํ”„๋กœํผํ‹ฐ๋ฅผ ์•„๋ฌด๋ฆฌ ๋งŽ์ด ์„ ์–ธํ•ด๋†”๋„ ์‚ฌ์šฉ ์•ˆ ํ•˜๋ฉด ๋ฉ”๋ชจ๋ฆฌ์— ์˜ฌ๋ฆฌ์ง„ ์•Š์Œ.

์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ + ์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ

struct User {     
	var nickname: String  
	static var originName: String = "์ง„์งœ ์ด๋ฆ„"     
	//์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ + ์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ    
	//๊ฐ’์„ ์ดˆ๊ธฐํ™”ํ•˜๊ณ  ์ €์žฅํ•  ์ˆ˜ ์žˆ๋Š” ๊ณต๊ฐ„์ด ์—†๊ณ , ๋‹ค๋ฅธ ์ €์žฅ ํ”„๋กœํผํ‹ฐ์˜ ๊ฐ’์„ ์—ฐ์‚ฐํ•ด์„œ ๊ฐ„์ ‘์ ์œผ๋กœ ๊ฐ’์„ ์ œ๊ณต!   
    
	var userIntroduce: String {     
		get {         
			return "์ด ์‚ฌ์šฉ์ž์˜ ๋‹‰๋„ค์ž„์€ \(nickname)์ด๊ณ , ์ง„์งœ ์ด๋ฆ„์€ \(User.originName)์ž…๋‹ˆ๋‹ค."   
		}  
	}
}
  • ๊ณผ์ œ์— movieDescription “๊ฐœ๋ด‰์ผ|๋Ÿฌ๋‹ํƒ€์ž„|ํ‰์ ”์ด๋Ÿฐ ๋ฌธ์ž์—ด ์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ๋กœ ๋ฏธ๋ฆฌ ๋งŒ๋“ค์–ด ๋†“์„ ์ˆ˜ ์žˆ์Œ → ์Šคํƒ๋ทฐ๋กœ ๋ถ™์—ฌ๋†“์€ ๋ถ„๋“ค์ด ์žˆ์—ˆ๋Š”๋ฐ ์Šคํƒ๋ทฐ ์“ด ๊ฑฐ๋Š” ์•ˆ์“ด๊ฑฐ๋ณด๋‹ค ๋กœ๋“œ๊ฐ€ ๋Š๋ฆผ. ๋˜‘๊ฐ™์ด ํ‘œ์‹œ ํ•  ์ˆ˜ ์žˆ์œผ๋ฉด ๋ทฐ ๊ฐœ์ˆ˜๋ฅผ ์ตœ๋Œ€ํ•œ ์ค„์ด๋Š”๊ฒŒ ์•„์ดํฐ์ž…์žฅ์—์„œ๋Š” ์ข‹์Œ.

์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ

struct BMI {  
	var weight: Double    
	var height: Double 		 	
	//์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ  
	var BMIResult: String {  
		get {            
		let bmiValue = weight / (height * height)       
		let bmiStatus = bmiValue < 18.5 ? "์ €์ฒด์ค‘" : "์ •์ƒ ์ด์ƒ"    
		return "๊ณ ๋ž˜๋ฐฅ๋‹˜์˜ BMI ์ง€์ˆ˜๋Š” \(bmiValue)๋กœ \(bmiStatus)์ž…๋‹ˆ๋‹ค."    
		}     
	}
}
  • ์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ๊ฐ€ ์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ๋ฉด ์ค‘๊ด„ํ˜ธ ์•ˆ์— ์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ ๋ฐ–์— ๋ชป ์”€.
  • ์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ๊ฐ€ get ๋ฐ–์— ์—†์œผ๋ฉด get ์ƒ๋žต ๊ฐ€๋Šฅ

์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ vs ํ•จ์ˆ˜์˜ ๋ฐ˜ํ™˜ ๊ฐ’ → ๊ฑฐ์˜ ๋น„์Šทํ•œ ์—ญํ• ์ด๊ธด ํ•จ.

  • ์—ฐ์‚ฐ ํ”„๋กœํผํ‹ฐ : ์ €์žฅํ”„๋กœํผํ‹ฐ ๋งŒ์œผ๋กœ ๋‹จ์ˆœํ•˜๊ฒŒ ์—ฐ์‚ฐ ๊ฐ€๋Šฅ ํ•œ ์ •๋„.
  • ํ•จ์ˆ˜ : ์ข€ ๋” ๋ณต์žกํ•œ ๊ฒƒ ํ•  ๋•Œ ๋งŽ์ด ์„ ํ˜ธ ๋จ.

Enum: ์ปดํŒŒ์ผ

  • ์ดˆ๊ธฐํ™” ๋ถˆ๊ฐ€๋Šฅ, ์ธ์Šคํ„ด์Šค ์ƒ์„ฑ ๋ถˆ๊ฐ€๋Šฅ → ์ธ์Šคํ„ด์Šค ํ”„๋กœํผํ‹ฐ/์ธ์Šคํ„ด์Šค ๋ฉ”์„œ๋“œ ์‚ฌ์šฉ ๋ถˆ๊ฐ€๋Šฅ!
  • ๊ฐ’ํƒ€์ž…
  • ํƒ€์ž… ํ”„๋กœํผํ‹ฐ ์‚ฌ์šฉ ๊ฐ€๋Šฅ(but ์ปดํŒŒ์ผ ํƒ€์ž…์ด๋ผ ๋‹ต์ด ๋“ค์–ด ์žˆ์–ด์•ผ ํ•จ.) → ๊ทธ๋Ÿผ rawValue ๋„ฃ์–ด ์ฃผ๋Š” ๊ฒƒ์ด๋ž‘ ๋ญ” ์ฐจ์ด? rawValue๋Š” ์œ ๋‹ˆํฌ ํ•ด์•ผ๋˜์„œ ๊ฐ™์€ rawValue๋ฅผ ๋‹ด์„ ์ˆ˜ ์—†์–ด์„œ case๋กœ ๋ฌธ๊ตฌ๋“ค์„ ๋‚˜ํƒ€๋‚ด๋‹ค๊ฐ€ static let์œผ๋กœ ์ „ํ™˜ํ•ด์•ผ ํ•˜๋Š” ๊ฒฝ์šฐ๊ฐ€ ์ƒ๊ธธ ์ˆ˜ ์žˆ์Œ
  • ๊ฐ™์€ ๊ฐ’์„ static let์„ ํ†ตํ•ด์„œ ๋‹ค๋ฅด๊ฒŒ ํ‘œํ˜„ ๊ฐ€๋Šฅ.

์ถ”๊ฐ€ ์กฐ์‚ฌํ•œ ์—ด๊ฑฐํ˜• ํŠน์ง•๊ณผ ์žฅ์ 

  • ์—ด๊ฑฐํ˜•์„ ์ด์šฉํ•˜์—ฌ ๋ฐ์ดํ„ฐ ํƒ€์ž…์„ ์ •์˜ํ•˜๋ฉด ์ปดํŒŒ์ผ ์˜ค๋ฅ˜๋กœ ์ฐพ์•„๋‚ด๋Š”๋ฐ ์šฉ์ด
  • ํŠน์ • ์ƒ์ˆ˜๋“ค์˜ ์ง‘ํ•ฉ
  • ๊ด€๋ จ ๊ฐ’์„ ํ•˜๋‚˜์˜ ์œ ํ˜•์œผ๋กœ ๋ฌถ์–ด์„œ ์ •์˜ํ•œ ํƒ€์ž…
  • ๊ฐ„๊ฒฐํ•˜๊ณ  ๊ฐ€๋…์„ฑ ๋†’์€ ์ฝ”๋“œ
  • ๋ฐฐ์—ด์˜ ๊ฒฝ์šฐ nil๊ฐ’์ด ๋“ค์–ด์žˆ๋Š” ๊ฒฝ์šฐ..๋“ฑ๋“ฑ..๋Ÿฐํƒ€์ž„ ์—๋Ÿฌ๊ฐ€ ๋ฐœ์ƒํ•  ์—ฌ์ง€๊ฐ€ ์žˆ์ง€๋งŒ, enum์€ ์ด๋Ÿฐ ์˜ค๋ฅ˜๋ฅผ ์ปดํŒŒ์ผ๋Ÿฌ๊ฐ€ ์žก์•„์ฃผ๊ธฐ ๋•Œ๋ฌธ์— ์ปดํŒŒ์ผํƒ€์ž„์— ์—๋Ÿฌ๋ฅผ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค.
  • struct๋กœ enum์˜ ๊ธฐ๋Šฅ์ ์ธ ์š”์†Œ๋Š” ๋Œ€์‘ํ•  ์ˆ˜ ์žˆ์ง€๋งŒ enum์˜ ๊ฒฝ์šฐ ์ธ์Šคํ„ด์Šค๋ฅผ ์ƒ์„ฑํ•˜์ง€ ์•Š๊ณ  ์ƒ์ˆ˜๋กœ ์ ‘๊ทผํ•  ์ˆ˜ ์žˆ๋„๋ก ๋งŒ๋“ค์–ด์ ธ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ํœด๋จผ์—๋Ÿฌ์˜ ์—ฌ์ง€๊ฐ€ ์ค„์–ด๋“ ๋‹ค.
  • stuct์™€ class๋กœ๋„ enum ์—ญํ• ์„ ํ•  ์ˆ˜ ์žˆ์ง€๋งŒ enum์€ ์ธ์Šคํ„ด์Šคํ™”๊ฐ€ ํ•„์š”ํ•˜์ง€ ์•Š๊ณ  ์ปดํŒŒ์ผ ๋‹น์‹œ์—๋„ ๋ฉค๋ฒ„๊ฐ€ ์ •์˜๋˜์–ด ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์˜ค๋ฅ˜์˜ ๊ฐ€๋Šฅ์„ฑ์ด ๋งค์šฐ ์ค„์–ด๋“ ๋‹ค.

์ž˜ ์งœ๋ ค๊ณ  ๊ณ ๋ฏผํ•˜๊ณ  ์•ˆ ์งœ๋Š” ๊ฒƒ๋ณด๋‹ค ์ด์ƒํ•˜๋”๋ผ๋„ ๋ง‰ ์งœ๋Š”๊ฒŒ ๋‚˜์ค‘์— ์†๋„์™€ ์‹ค๋ ฅ ํ–ฅ์ƒ์— ์ค‘์š”.

๊ฐ™์€ ์Šค๋ณด์— ์žˆ๋Š” ๋ทฐ์ปจ์ด๋ฉด ์œ„์— ์ฃผ์„์ฒ˜๋Ÿผ ์•ˆ ์“ฐ๊ณ  ๊ทธ๋ƒฅ storyboard ํ˜ธ์ถœํ•ด์„œ ์ ‘๊ทผ ๊ฐ€๋Šฅ.

Enum์œผ๋กœ ํ—ค๋” ์žˆ๋Š” ํ…Œ์ด๋ธ”๋ทฐ ๊น”๊ผผํ•˜๊ฒŒ ๋งŒ๋“ค๊ธฐ

๋งŒ๋“ค ํ™”๋ฉด

์—ด๊ฑฐํ˜• ๊ตฌํ˜„

  • ์„น์…˜ ๊ฒฝ์šฐ๋“ค์„ case๋กœ ๋‚˜๋ˆ„์–ด ์—ด๊ฑฐํ˜• ์•ˆ์— ์„ ์–ธํ•ด๋‘ .
  • mainOptions ํ”„๋กœํผํ‹ฐ: ํ—ค๋”์šฉ. ๊ฐ ์„น์…˜ ์ผ€์ด์Šค ํ—ค๋” ๋ฌธ์ž์—ด ๋ฐ˜ํ™˜
  • subOptions ํ”„๋กœํผํ‹ฐ: ์…€ ํ…์ŠคํŠธ ์šฉ. ๊ฐ ์„น์…˜ ์ผ€์ด์Šค ํ•ด๋‹น ๋ฌธ์ž์—ด ๋ฐฐ์—ด ๋ฐ˜ํ™˜

๋ฆฌํŒฉํ† ๋ง ์ „ ์ฝ”๋“œ

import UIKit 
class SettingTableViewController: UITableViewController { 
	let sectionHeaderList = [(name:"์ „์ฒด ์„ค์ •",count:3),(name:"๊ฐœ์ธ ์„ค์ •",count:3),(name:"๊ธฐํƒ€",count:3)] 
	let allSettingList = ["๊ณต์ง€์‚ฌํ•ญ","์‹คํ—˜์‹ค","๋ฒ„์ „ ์ •๋ณด"]     
	let personalSettingList = ["๊ฐœ์ธ/๋ณด์•ˆ","์•Œ๋ฆผ","์ฑ„ํŒ…","๋ฉ€ํ‹ฐ ํ”„๋กœํ•„"]   
	let etcSettingList = ["๊ณ ๊ฐ์„ผํ„ฐ/๋„์›€๋ง"]    
	override func viewDidLoad() {     
		super.viewDidLoad()     
	} 

    // MARK: - Table view data source    
	override func numberOfSections(in tableView: UITableView) -> Int { 
		return sectionHeaderList.count 
	}    

	override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {        
		switch(section){         
		case 0: return allSettingList.count      
		case 1: return personalSettingList.count        
		case 2: return etcSettingList.count         
		default: return sectionHeaderList[section].count    
		}                          
	} 

	override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {        
    	let cell = tableView.dequeueReusableCell(withIdentifier: "SettingContentsCell", for: indexPath)                
  	  		switch indexPath.section{      
  				 case 0: cell.textLabel?.text = allSettingList[indexPath.row]       
  	 	 	  	 case 1: cell.textLabel?.text = personalSettingList[indexPath.row]       
  	 			 case 2: cell.textLabel?.text = etcSettingList[indexPath.row]       
 			     default: cell.textLabel?.text = allSettingList[indexPath.row]     
   			 }         
   	 	return cell   
    }         
    override func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {   
		return sectionHeaderList[section].name   
	}  
}

๋ฆฌํŒฉํ† ๋ง ํ›„ ์ฝ”๋“œ

import UIKit  
enum SettingOptions: Int, CaseIterable {    
	case total, personal, others    
	var mainOptions: String {       
		get {            
			switch self{      
				case .total: return "์ „์ฒด ์„ค์ •"          
				case .personal: return "๊ฐœ์ธ ์„ค์ •"         
				case .others: return "๊ธฐํƒ€"          
			}       
		}    
	}   
	var subOptions: [String] {        
		switch self {     
			case .total: return ["๊ณต์ง€์‚ฌํ•ญ","์‹คํ—˜์‹ค","๋ฒ„์ „ ์ •๋ณด"]       
			case .personal: return ["๊ฐœ์ธ/๋ณด์•ˆ","์•Œ๋ฆผ","์ฑ„ํŒ…","๋ฉ€ํ‹ฐํ”„๋กœํ•„"] 
			case .others: return ["๊ณ ๊ฐ์„ผํ„ฐ/๋„์›€๋ง"]   
			}   
		} 
	} 
class SettingTableViewController: UITableViewController {   
	override func viewDidLoad() {     
		super.viewDidLoad()          
	}     
	override func numberOfSections(in tableView: UITableView) -> Int {      
		return SettingOptions.allCases.count  
	}     
	override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {        
		return SettingOptions.allCases[section].subOptions.count   
	}     
	override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {      
		let cell = tableView.dequeueReusableCell(withIdentifier: SettingTableViewCell.identifier)!     
		cell.textLabel?.text = SettingOptions.allCases[indexPath.section].subOptions[indexPath.row]        
		return cell   
	}    
}

์…€ ์•ˆ์˜ ๋ฒ„ํŠผ ์•ก์…˜ ๋ฐ›๊ธฐ (๋ทฐ tag ์ด์šฉํ•ด์„œ ๊ตฌํ˜„ํ•˜๊ธฐ)

  • ์–ด๋–ค ๋ฒ„ํŠผ์ธ์ง€ ๊ตฌ๋ถ„ํ•˜๊ธฐ ์œ„ํ•ด tag๊ฐ’ ๋„ฃ์–ด ์คŒ.
  • sender ๋งค๊ฐœ๋ณ€์ˆ˜๋Š” iOS ๋‚ด๋ถ€์ ๋™์ž‘ํ•˜์—ฌ ๊ฐ’์ด ๋“ค์–ด์˜ค๋Š” ๋ถ€๋ถ„
  • ์œ„์—์„œ ์ง€์ •ํ•œ tag๊ฐ’ ํ”„๋ฆฐํŠธ ํ•ด๋ณด๋Š” ์ค‘

  • ๋‹จ์  : ์„น์…˜ ์—ฌ๋Ÿฌ ๊ฐœ์—ฌ์„œ ํƒœ๊ทธ ๊ฒน์น˜๊ณ ํ•˜๋ฉด ๋”ฐ๋กœ ๊ด€๋ฆฌํ•ด์ฃผ๊ฑฐ๋‚˜ ์ž„์˜์˜ ์ˆซ์ž ๋‹ค ์ง€์ •ํ•ด์ค˜์•ผํ•จ.

SearchBar

  • ์•„์›ƒ๋ › ์•ก์…˜ ์—ฐ๊ฒฐ ์•ˆ๋จ
  • ํ•˜์ง€๋งŒ ์„œ์น˜๋ฐ” ์•ˆ์— ์žˆ๋Š”๊ฒŒ ํ…์ŠคํŠธํ•„๋“œ → ํ…์ŠคํŠธํ•„๋“œ ๊ธฐ๋Šฅ ์ด์šฉ ๊ฐ€๋Šฅ

  • addTarget์œผ๋กœ ์•ก์…˜ ๊ตฌํ˜„ ๊ฐ€๋Šฅ.
  • .editingDidEndOnExit : ์—”ํ„ฐํ‚ค ๋ˆ„๋ฅธ ์ƒํƒœ

searchbar ๋‚ด์šฉ ํ…Œ์ด๋ธ”๋ทฐ ๋ฐ์ดํ„ฐ ๋ฆฌ์ŠคํŠธ์— ๋„ฃ์€ ํ›„ ํ…Œ์ด๋ธ”๋ทฐ Reload

didSet

๋ฐ์ดํ„ฐ ๋ฐ”๋€Œ๋ฉด ๊ณ„์† ์‹คํ–‰ ๋˜๋Š” ์ฝ”๋“œ

ํ…Œ์ด๋ธ” ๋ทฐ ์Šค์™€์ดํ”„ํ•ด์„œ ์ง€์šฐ๊ฑฐ๋‚˜ ๋‚ด์šฉ ์ถ”๊ฐ€ ๋˜๊ฑฐ๋‚˜ ์ข‹์•„์š” ๋ˆ„๋ฅด๊ฑฐ๋‚˜ ๋Œ๋•Œ๋งˆ๋‹ค ํ˜ธ์ถœ ๋จ.

→ viewcontroller ์ฝ”๋“œ ๋‚ด์—์„œ ๊ตณ์ด ๋”ฐ๋กœ tableView.reloadData() ์•ˆ ํ•ด์ค˜๋„ ์ž๋™์œผ๋กœ ๋ฐ˜์˜ ๋จ.

'SeSAC' ์นดํ…Œ๊ณ ๋ฆฌ์˜ ๋‹ค๋ฅธ ๊ธ€

[iOS] TIL_230803  (0) 2023.08.06
[iOS] TIL_230802  (0) 2023.08.05
[iOS] TIL_230731  (0) 2023.08.03
[iOS] TIL_230728  (0) 2023.08.01
[iOS] TIL_230727  (0) 2023.07.31