Swift隨手紀錄Day24-Firebase-Authentication-Login & Logout
防止偷懶Day24 今天來完成整個註冊、登入、登出程序 首先先來釐清需求 使用者打開APP時應該會進入HomeController 這時我們應該先判斷這使用者是否有帳號登入過 如果有就在navigationItem上更新這名使用者的名稱 如果沒有就把畫面送到LoginController
防止偷懶Day24
今天來完成整個註冊、登入、登出程序
首先先來釐清需求
使用者打開APP時應該會進入HomeController
這時我們應該先判斷這使用者是否有帳號登入過
如果有就在navigationItem上更新這名使用者的名稱
如果沒有就把畫面送到LoginController
首先來修改HomeController.swift裡面的程式碼
override
func
viewDidLoad
super
let
=
UIBarButtonItem
"New Team"
self
#selector
navigationItem.rightBarButtonItem =
let
=
UIBarButtonItem
"Logout"
self
#selector
navigationItem.leftBarButtonItem =
checkUserIsLogin()
}
func
checkUserIsLogin
if
FIRAuth
?
?
==
nil
perform(#selector
nil
0
} else
fetchUserSetNavBarTitle()
}
}
func
fetchUserSetNavBarTitle
guard
let
=
FIRAuth
?
?
else
return
}
FIRDatabase
"User"
in
print
if
let
=
as?
Any
self
=
"name"
as?
String
}
}, withCancel: nil
}
func
handleLogout
do
try
FIRAuth
?
} catch
let
print
}
let
=
LoginController
loginController.homeController =
self
present(loginController, animated: true
nil
}
我新增了兩個新的function跟修改了一個之前寫的function
這裡新增的兩個新的function分別是checkUserIsLogin以及fetchUserSetNavBarTitle
在viewDidLoad時會執行checkUserIsLogin這個function
裡面負責跟Firebase確認這支手機是否有登入過
如果沒有就去執行handleLogout讓畫面移動到LoginController
如果有就執行另一個新增的fetchUserSetNavBarTitle來更新從Firebase拿到的使用者名稱
然後是修改後的handleLogout多做了兩件事情
第一件事情是跟Firebase做登出的動作
第二件事是在實作LoginController時把hemeController的reference加進去
這樣做的目的是等等我們再處理完LoginController的登入或註冊之後可以直接來更新navigationItem的名稱
p.s.記得import Firebase
再來就進入LoginController.swift來處理登入跟註冊的程序
一樣先上程式碼
import
import
class
LoginController
AddMemberController
var
HomeController
var
NSLayoutConstraint
var
NSLayoutConstraint
let
UISegmentedControl
=
let
=
UISegmentedControl
"Login"
"Register"
sc.selectedSegmentIndex =
0
sc.translatesAutoresizingMaskIntoConstraints =
false
sc.addTarget(self
#selector
return
}()
let
UITextField
=
let
=
UITextField
text.placeholder =
"email"
text.translatesAutoresizingMaskIntoConstraints =
false
text.layer.borderColor =
UIColor
text.layer.borderWidth =
1
return
}()
let
UITextField
=
let
=
UITextField
text.placeholder =
"password"
text.translatesAutoresizingMaskIntoConstraints =
false
text.isSecureTextEntry =
true
text.layer.borderColor =
UIColor
text.layer.borderWidth =
1
return
}()
lazy
var
UIButton
=
let
=
UIButton
button.translatesAutoresizingMaskIntoConstraints =
false
button.setTitle("Login"
button.backgroundColor =
button.addTarget(self
#selector
return
}()
func
handleLoginRegister
if
==
0
handleLogin()
} else
handleRegister()
}
}
func
handleLogin
guard
let
=
let
=
else
return
}
FIRAuth
?
in
if
!=
nil
return
}
self
?
self
true
nil
})
}
func
handleRegister
guard
let
=
let
=
let
=
else
return
}
FIRAuth
?
FIRUser
in
if
!=
nil
print
!
return
}
guard
let
=
?
else
return
}
let
=
FIRDatabase
"https://hbcrecord-5a3d4.firebaseio.com/"
let
=
"User"
let
=
"email"
"name"
userReference.updateChildValues(accountValue, withCompletionBlock: { (err, ref) in
if
!=
nil
print
!
return
}
self
?
=
"name"
self
true
nil
})
})
}
func
handleChangeButtonTitle
if
==
0
loginButton.setTitle("Login"
nameText.isHidden =
true
profileImageTopAnchor?
=
64
emailTopAnchor?
=
8
} else
loginButton.setTitle("Register"
nameText.isHidden =
false
profileImageTopAnchor?
=
32
emailTopAnchor?
=
48
view.layoutIfNeeded()
}
}
override
func
viewDidLoad
super
profileImage.removeFromSuperview()
profileImage.removeConstraints(profileImage.constraints)
positionSegmentedControl.removeFromSuperview()
nameText.removeFromSuperview()
registerButton.removeFromSuperview()
view.addSubview(profileImage)
view.addSubview(loginSegmentedControl)
view.addSubview(nameText)
view.addSubview(emailText)
view.addSubview(passwordText)
view.addSubview(loginButton)
nameText.isHidden =
true
profileImageTopAnchor =
64
profileImageTopAnchor?
=
true
profileImage.centerXAnchor.constraint(equalTo: view.centerXAnchor).isActive =
true
profileImage.heightAnchor.constraint(equalToConstant: 110
=
true
profileImage.widthAnchor.constraint(equalToConstant: 110
=
true
loginSegmentedControl.topAnchor.constraint(equalTo: profileImage.bottomAnchor, constant: 8
=
true
loginSegmentedControl.leftAnchor.constraint(equalTo: view.leftAnchor, constant: 22
=
true
loginSegmentedControl.rightAnchor.constraint(equalTo: view.rightAnchor, constant: -
22
=
true
loginSegmentedControl.heightAnchor.constraint(equalToConstant: 24
=
true
nameText.topAnchor.constraint(equalTo: loginSegmentedControl.bottomAnchor, constant: 8
=
true
nameText.leftAnchor.constraint(equalTo: view.leftAnchor, constant: 22
=
true
nameText.rightAnchor.constraint(equalTo: view.rightAnchor, constant: -
22
=
true
emailTopAnchor =
8
emailTopAnchor?
=
true
emailText.leftAnchor.constraint(equalTo: view.leftAnchor, constant: 22
=
true
emailText.rightAnchor.constraint(equalTo: view.rightAnchor, constant: -
22
=
true
emailText.heightAnchor.constraint(equalToConstant: 32
=
true
passwordText.topAnchor.constraint(equalTo: emailText.bottomAnchor, constant: 8
=
true
passwordText.leftAnchor.constraint(equalTo: view.leftAnchor, constant: 22
=
true
passwordText.rightAnchor.constraint(equalTo: view.rightAnchor, constant: -
22
=
true
passwordText.heightAnchor.constraint(equalToConstant: 32
=
true
loginButton.topAnchor.constraint(equalTo: passwordText.bottomAnchor, constant: 8
=
true
loginButton.leftAnchor.constraint(equalTo: view.leftAnchor, constant: 22
=
true
loginButton.rightAnchor.constraint(equalTo: view.rightAnchor, constant: -
22
=
true
loginButton.heightAnchor.constraint(equalToConstant: 50
=
true
}
}
這裡一樣新增兩個新function跟修改一個舊function
不過為了可以更新HomeController的navigationItem.title
先新增一個homeController的物件
然後把按下註冊/登入按鈕的動作從舊的handleRegister換成新增的handleLoginRegister
在handleLoginRegister裡面用loginSegmentedControl所選擇的是login還是register來決定要呼叫哪個function
如果是登入就呼叫新增的第二個functionhandleLogin來跟Firebase做登入的動作以及剛剛提到的更新navigationItem.title
如果是註冊就呼叫之前寫的handleRegister
但這邊也對handleRegister做了點修改,首先是多傳了name這個值
再來是註冊成功也會去修改homeController的navigationItem.title
不過跟handleLogin裡面直接呼叫fetchUserSetNavBarTitle不同的是
因為註冊時自己就有name這個數值,就不需要多跟Firebase要一次資料了
所以直接把要傳出去註冊的name拿來用就好
來看看完成品吧
