mirror of
https://gitlab.linphone.org/BC/public/linphone-iphone.git
synced 2026-01-17 11:08:06 +00:00
Add Profile mode view and change popupview for reuse
This commit is contained in:
parent
ae5f3a6c41
commit
7bc754195b
19 changed files with 581 additions and 241 deletions
|
|
@ -34,6 +34,8 @@
|
|||
D7D24D162AC1B4E800C6F35B /* NotoSans-SemiBold.ttf in Resources */ = {isa = PBXBuildFile; fileRef = D7D24D102AC1B4E800C6F35B /* NotoSans-SemiBold.ttf */; };
|
||||
D7D24D172AC1B4E800C6F35B /* NotoSans-Bold.ttf in Resources */ = {isa = PBXBuildFile; fileRef = D7D24D112AC1B4E800C6F35B /* NotoSans-Bold.ttf */; };
|
||||
D7D24D182AC1B4E800C6F35B /* NotoSans-ExtraBold.ttf in Resources */ = {isa = PBXBuildFile; fileRef = D7D24D122AC1B4E800C6F35B /* NotoSans-ExtraBold.ttf */; };
|
||||
D7DA67622ACCB2FA00E95002 /* LoginFragment.swift in Sources */ = {isa = PBXBuildFile; fileRef = D7DA67612ACCB2FA00E95002 /* LoginFragment.swift */; };
|
||||
D7DA67642ACCB31700E95002 /* ProfileModeFragment.swift in Sources */ = {isa = PBXBuildFile; fileRef = D7DA67632ACCB31700E95002 /* ProfileModeFragment.swift */; };
|
||||
/* End PBXBuildFile section */
|
||||
|
||||
/* Begin PBXFileReference section */
|
||||
|
|
@ -68,6 +70,8 @@
|
|||
D7D24D102AC1B4E800C6F35B /* NotoSans-SemiBold.ttf */ = {isa = PBXFileReference; lastKnownFileType = file; path = "NotoSans-SemiBold.ttf"; sourceTree = "<group>"; };
|
||||
D7D24D112AC1B4E800C6F35B /* NotoSans-Bold.ttf */ = {isa = PBXFileReference; lastKnownFileType = file; path = "NotoSans-Bold.ttf"; sourceTree = "<group>"; };
|
||||
D7D24D122AC1B4E800C6F35B /* NotoSans-ExtraBold.ttf */ = {isa = PBXFileReference; lastKnownFileType = file; path = "NotoSans-ExtraBold.ttf"; sourceTree = "<group>"; };
|
||||
D7DA67612ACCB2FA00E95002 /* LoginFragment.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LoginFragment.swift; sourceTree = "<group>"; };
|
||||
D7DA67632ACCB31700E95002 /* ProfileModeFragment.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ProfileModeFragment.swift; sourceTree = "<group>"; };
|
||||
FBDE73581C1DC4F98CC3DF3A /* Pods-Linphone.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Linphone.debug.xcconfig"; path = "Target Support Files/Pods-Linphone/Pods-Linphone.debug.xcconfig"; sourceTree = "<group>"; };
|
||||
/* End PBXFileReference section */
|
||||
|
||||
|
|
@ -187,6 +191,7 @@
|
|||
D719ABCA2ABC761800B41C10 /* Assistant */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
D7DA67602ACCB2D700E95002 /* Fragments */,
|
||||
D719ABCD2ABC777600B41C10 /* Viewmodel */,
|
||||
D719ABCB2ABC769C00B41C10 /* AssistantView.swift */,
|
||||
);
|
||||
|
|
@ -265,6 +270,15 @@
|
|||
path = Fonts;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
D7DA67602ACCB2D700E95002 /* Fragments */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
D7DA67612ACCB2FA00E95002 /* LoginFragment.swift */,
|
||||
D7DA67632ACCB31700E95002 /* ProfileModeFragment.swift */,
|
||||
);
|
||||
path = Fragments;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
/* End PBXGroup section */
|
||||
|
||||
/* Begin PBXNativeTarget section */
|
||||
|
|
@ -399,10 +413,12 @@
|
|||
D7A03FC02ACC2E390081A588 /* HistoryView.swift in Sources */,
|
||||
D74C9CF82ACACECE0021626A /* WelcomePage1Fragment.swift in Sources */,
|
||||
D717071E2AC5922E0037746F /* ColorExtension.swift in Sources */,
|
||||
D7DA67642ACCB31700E95002 /* ProfileModeFragment.swift in Sources */,
|
||||
D74C9CFC2ACACF370021626A /* WelcomePage3Fragment.swift in Sources */,
|
||||
D719ABCC2ABC769C00B41C10 /* AssistantView.swift in Sources */,
|
||||
D74C9CFA2ACACF2D0021626A /* WelcomePage2Fragment.swift in Sources */,
|
||||
D74C9CFF2ACAEC5E0021626A /* PopupView.swift in Sources */,
|
||||
D7DA67622ACCB2FA00E95002 /* LoginFragment.swift in Sources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
{
|
||||
"images" : [
|
||||
{
|
||||
"filename" : "linphone.svg",
|
||||
"filename" : "Linphone.svg",
|
||||
"idiom" : "universal",
|
||||
"scale" : "1x"
|
||||
},
|
||||
|
|
|
|||
21
Linphone/Assets.xcassets/info.imageset/Contents.json
vendored
Normal file
21
Linphone/Assets.xcassets/info.imageset/Contents.json
vendored
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
{
|
||||
"images" : [
|
||||
{
|
||||
"filename" : "info.svg",
|
||||
"idiom" : "universal",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "universal",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "universal",
|
||||
"scale" : "3x"
|
||||
}
|
||||
],
|
||||
"info" : {
|
||||
"author" : "xcode",
|
||||
"version" : 1
|
||||
}
|
||||
}
|
||||
1
Linphone/Assets.xcassets/info.imageset/info.svg
vendored
Normal file
1
Linphone/Assets.xcassets/info.imageset/info.svg
vendored
Normal file
|
|
@ -0,0 +1 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" width="32" height="32" fill="#000000" viewBox="0 0 256 256"><path d="M128,24A104,104,0,1,0,232,128,104.11,104.11,0,0,0,128,24Zm0,192a88,88,0,1,1,88-88A88.1,88.1,0,0,1,128,216Zm16-40a8,8,0,0,1-8,8,16,16,0,0,1-16-16V128a8,8,0,0,1,0-16,16,16,0,0,1,16,16v40A8,8,0,0,1,144,176ZM112,84a12,12,0,1,1,12,12A12,12,0,0,1,112,84Z"></path></svg>
|
||||
|
After Width: | Height: | Size: 372 B |
21
Linphone/Assets.xcassets/profile-mode.imageset/Contents.json
vendored
Normal file
21
Linphone/Assets.xcassets/profile-mode.imageset/Contents.json
vendored
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
{
|
||||
"images" : [
|
||||
{
|
||||
"filename" : "profile-mode.png",
|
||||
"idiom" : "universal",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "universal",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "universal",
|
||||
"scale" : "3x"
|
||||
}
|
||||
],
|
||||
"info" : {
|
||||
"author" : "xcode",
|
||||
"version" : 1
|
||||
}
|
||||
}
|
||||
BIN
Linphone/Assets.xcassets/profile-mode.imageset/profile-mode.png
vendored
Normal file
BIN
Linphone/Assets.xcassets/profile-mode.imageset/profile-mode.png
vendored
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 152 KiB |
21
Linphone/Assets.xcassets/radio-button-fill.imageset/Contents.json
vendored
Normal file
21
Linphone/Assets.xcassets/radio-button-fill.imageset/Contents.json
vendored
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
{
|
||||
"images" : [
|
||||
{
|
||||
"filename" : "radio-button-fill.svg",
|
||||
"idiom" : "universal",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "universal",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "universal",
|
||||
"scale" : "3x"
|
||||
}
|
||||
],
|
||||
"info" : {
|
||||
"author" : "xcode",
|
||||
"version" : 1
|
||||
}
|
||||
}
|
||||
10
Linphone/Assets.xcassets/radio-button-fill.imageset/radio-button-fill.svg
vendored
Normal file
10
Linphone/Assets.xcassets/radio-button-fill.imageset/radio-button-fill.svg
vendored
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<g id="radiobutton" clip-path="url(#clip0_2022_35988)">
|
||||
<path id="Vector" d="M12 7C9.24 7 7 9.24 7 12C7 14.76 9.24 17 12 17C14.76 17 17 14.76 17 12C17 9.24 14.76 7 12 7ZM12 2C6.48 2 2 6.48 2 12C2 17.52 6.48 22 12 22C17.52 22 22 17.52 22 12C22 6.48 17.52 2 12 2ZM12 20C7.58 20 4 16.42 4 12C4 7.58 7.58 4 12 4C16.42 4 20 7.58 20 12C20 16.42 16.42 20 12 20Z" fill="#FE5E00"/>
|
||||
</g>
|
||||
<defs>
|
||||
<clipPath id="clip0_2022_35988">
|
||||
<rect width="24" height="24" fill="white"/>
|
||||
</clipPath>
|
||||
</defs>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 585 B |
21
Linphone/Assets.xcassets/radio-button.imageset/Contents.json
vendored
Normal file
21
Linphone/Assets.xcassets/radio-button.imageset/Contents.json
vendored
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
{
|
||||
"images" : [
|
||||
{
|
||||
"filename" : "radio-button.svg",
|
||||
"idiom" : "universal",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "universal",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "universal",
|
||||
"scale" : "3x"
|
||||
}
|
||||
],
|
||||
"info" : {
|
||||
"author" : "xcode",
|
||||
"version" : 1
|
||||
}
|
||||
}
|
||||
10
Linphone/Assets.xcassets/radio-button.imageset/radio-button.svg
vendored
Normal file
10
Linphone/Assets.xcassets/radio-button.imageset/radio-button.svg
vendored
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<g id="radiobutton" clip-path="url(#clip0_2022_35992)">
|
||||
<path id="Vector" d="M12 2C6.48 2 2 6.48 2 12C2 17.52 6.48 22 12 22C17.52 22 22 17.52 22 12C22 6.48 17.52 2 12 2ZM12 20C7.58 20 4 16.42 4 12C4 7.58 7.58 4 12 4C16.42 4 20 7.58 20 12C20 16.42 16.42 20 12 20Z" fill="#FE5E00"/>
|
||||
</g>
|
||||
<defs>
|
||||
<clipPath id="clip0_2022_35992">
|
||||
<rect width="24" height="24" fill="white"/>
|
||||
</clipPath>
|
||||
</defs>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 493 B |
|
|
@ -88,6 +88,15 @@
|
|||
},
|
||||
"Calls" : {
|
||||
|
||||
},
|
||||
"Ce mode vous permet d’être interopérable avec d’autres services SIP.\nVos communications seront chiffrées de point à point. " : {
|
||||
|
||||
},
|
||||
"Chiffrement de bout en bout de tous vos échanges, grâce au mode default vos communications sont à l’abri des regards." : {
|
||||
|
||||
},
|
||||
"Close" : {
|
||||
|
||||
},
|
||||
"Conditions de service" : {
|
||||
|
||||
|
|
@ -97,6 +106,12 @@
|
|||
},
|
||||
"Contacts View" : {
|
||||
|
||||
},
|
||||
"Default" : {
|
||||
|
||||
},
|
||||
"Default mode" : {
|
||||
|
||||
},
|
||||
"Deny all" : {
|
||||
|
||||
|
|
@ -116,6 +131,12 @@
|
|||
},
|
||||
"History View" : {
|
||||
|
||||
},
|
||||
"Interoperable" : {
|
||||
|
||||
},
|
||||
"Interoperable mode" : {
|
||||
|
||||
},
|
||||
"Linphone" : {
|
||||
|
||||
|
|
@ -166,6 +187,12 @@
|
|||
},
|
||||
"TCP" : {
|
||||
|
||||
},
|
||||
"Texte explicatif du default mode : lorem ipsum dolor sit amet, consectetur adipiscing elit. Etiam velit sapien, egestas sit amet dictum eget, condimentum a ligula." : {
|
||||
|
||||
},
|
||||
"Texte explicatif du interoperable mode : lorem ipsum dolor sit amet, consectetur adipiscing elit. Etiam velit sapien, egestas sit amet dictum eget, condimentum a ligula." : {
|
||||
|
||||
},
|
||||
"TLS" : {
|
||||
|
||||
|
|
|
|||
|
|
@ -36,3 +36,7 @@ struct SplashScreen: View {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
#Preview {
|
||||
SplashScreen(isActive: .constant(true))
|
||||
}
|
||||
|
|
|
|||
|
|
@ -21,215 +21,12 @@ import SwiftUI
|
|||
|
||||
struct AssistantView: View {
|
||||
|
||||
@ObservedObject private var coreContext = CoreContext.shared
|
||||
@ObservedObject var accountLoginViewModel : AccountLoginViewModel
|
||||
|
||||
@State private var isSecured: Bool = true
|
||||
|
||||
@FocusState var isNameFocused:Bool
|
||||
@FocusState var isPasswordFocused:Bool
|
||||
|
||||
var body: some View {
|
||||
GeometryReader { geometry in
|
||||
ScrollView(.vertical) {
|
||||
VStack {
|
||||
ZStack {
|
||||
Image("mountain")
|
||||
.resizable()
|
||||
.scaledToFill()
|
||||
.frame(width: geometry.size.width, height: 100)
|
||||
.clipped()
|
||||
Text("assistant_account_login")
|
||||
.default_text_style_white_800(styleSize: 20)
|
||||
.padding(.top, 20)
|
||||
}
|
||||
.padding(.top, 35)
|
||||
.padding(.bottom, 10)
|
||||
|
||||
VStack(alignment: .leading) {
|
||||
Text(String(localized: "username")+"*")
|
||||
.default_text_style_700(styleSize: 15)
|
||||
.padding(.bottom, -5)
|
||||
|
||||
TextField("username", text : $accountLoginViewModel.username)
|
||||
.default_text_style(styleSize: 15)
|
||||
.disabled(coreContext.loggedIn)
|
||||
.frame(height: 25)
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 15)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(isNameFocused ? Color.orange_main_500 : Color.gray_200, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom)
|
||||
.focused($isNameFocused)
|
||||
|
||||
Text(String(localized: "password")+"*")
|
||||
.default_text_style_700(styleSize: 15)
|
||||
.padding(.bottom, -5)
|
||||
|
||||
ZStack(alignment: .trailing) {
|
||||
Group {
|
||||
if isSecured {
|
||||
SecureField("password", text: $accountLoginViewModel.passwd)
|
||||
.default_text_style(styleSize: 15)
|
||||
.frame(height: 25)
|
||||
.focused($isPasswordFocused)
|
||||
} else {
|
||||
TextField("password", text: $accountLoginViewModel.passwd)
|
||||
.default_text_style(styleSize: 15)
|
||||
.frame(height: 25)
|
||||
.focused($isPasswordFocused)
|
||||
}
|
||||
}
|
||||
Button(action: {
|
||||
isSecured.toggle()
|
||||
}) {
|
||||
Image(self.isSecured ? "eye-slash" : "eye")
|
||||
.renderingMode(.template)
|
||||
.resizable()
|
||||
.foregroundStyle(Color.gray_main2_500)
|
||||
.frame(width: 20, height: 20)
|
||||
}
|
||||
}
|
||||
.disabled(coreContext.loggedIn)
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 15)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(isPasswordFocused ? Color.orange_main_500 : Color.gray_200, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom)
|
||||
|
||||
Button(action: {
|
||||
if (self.coreContext.loggedIn){
|
||||
self.accountLoginViewModel.unregister()
|
||||
self.accountLoginViewModel.delete()
|
||||
} else {
|
||||
self.accountLoginViewModel.login()
|
||||
}
|
||||
}) {
|
||||
Text(coreContext.loggedIn ? "Log out" : "assistant_account_login")
|
||||
.default_text_style_white_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.background((accountLoginViewModel.username.isEmpty || accountLoginViewModel.passwd.isEmpty) ? Color.orange_main_100 : Color.orange_main_500)
|
||||
.cornerRadius(60)
|
||||
.disabled(accountLoginViewModel.username.isEmpty || accountLoginViewModel.passwd.isEmpty)
|
||||
.padding(.bottom)
|
||||
|
||||
Button(action: {
|
||||
|
||||
}) {
|
||||
Text("Forgotten password?")
|
||||
.underline()
|
||||
.default_text_style_600(styleSize: 15)
|
||||
.foregroundStyle(Color.gray_main2_500)
|
||||
}
|
||||
.frame(maxWidth: .infinity)
|
||||
.padding(.bottom, 30)
|
||||
|
||||
HStack {
|
||||
VStack{
|
||||
Divider()
|
||||
}
|
||||
Text(" or ")
|
||||
.default_text_style(styleSize: 15)
|
||||
.foregroundStyle(Color.gray_main2_500)
|
||||
VStack{
|
||||
Divider()
|
||||
}
|
||||
}
|
||||
.padding(.bottom, 10)
|
||||
|
||||
Button(action: {
|
||||
|
||||
}) {
|
||||
HStack {
|
||||
Image("qr-code")
|
||||
.renderingMode(.template)
|
||||
.resizable()
|
||||
.foregroundStyle(Color.orange_main_500)
|
||||
.frame(width: 20, height: 20)
|
||||
|
||||
Text("Scan QR code")
|
||||
.default_text_style_orange_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
}
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(Color.orange_main_500, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom)
|
||||
|
||||
Button(action: {
|
||||
|
||||
}) {
|
||||
Text("Use SIP Account")
|
||||
.default_text_style_orange_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(Color.orange_main_500, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom)
|
||||
|
||||
HStack(alignment: .center) {
|
||||
|
||||
Spacer()
|
||||
|
||||
Text("Not account yet?")
|
||||
.default_text_style(styleSize: 15)
|
||||
.foregroundStyle(Color.gray_main2_700)
|
||||
.padding(.horizontal, 10)
|
||||
|
||||
Button(action: {
|
||||
|
||||
}) {
|
||||
Text("Register")
|
||||
.default_text_style_orange_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(Color.orange_main_500, lineWidth: 1)
|
||||
)
|
||||
.padding(.horizontal, 10)
|
||||
|
||||
Spacer()
|
||||
}
|
||||
.padding(.bottom)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
}
|
||||
}
|
||||
}
|
||||
//LoginFragment(accountLoginViewModel: AccountLoginViewModel())
|
||||
ProfileModeFragment()
|
||||
}
|
||||
}
|
||||
|
||||
#Preview {
|
||||
AssistantView(accountLoginViewModel: AccountLoginViewModel())
|
||||
AssistantView()
|
||||
}
|
||||
|
|
|
|||
235
Linphone/UI/Assistant/Fragments/LoginFragment.swift
Normal file
235
Linphone/UI/Assistant/Fragments/LoginFragment.swift
Normal file
|
|
@ -0,0 +1,235 @@
|
|||
/*
|
||||
* Copyright (c) 2010-2023 Belledonne Communications SARL.
|
||||
*
|
||||
* This file is part of linphone-iphone
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import SwiftUI
|
||||
|
||||
struct LoginFragment: View {
|
||||
|
||||
@ObservedObject private var coreContext = CoreContext.shared
|
||||
@ObservedObject var accountLoginViewModel : AccountLoginViewModel
|
||||
|
||||
@State private var isSecured: Bool = true
|
||||
|
||||
@FocusState var isNameFocused:Bool
|
||||
@FocusState var isPasswordFocused:Bool
|
||||
|
||||
var body: some View {
|
||||
GeometryReader { geometry in
|
||||
ScrollView(.vertical) {
|
||||
VStack {
|
||||
ZStack {
|
||||
Image("mountain")
|
||||
.resizable()
|
||||
.scaledToFill()
|
||||
.frame(width: geometry.size.width, height: 100)
|
||||
.clipped()
|
||||
Text("assistant_account_login")
|
||||
.default_text_style_white_800(styleSize: 20)
|
||||
.padding(.top, 20)
|
||||
}
|
||||
.padding(.top, 35)
|
||||
.padding(.bottom, 10)
|
||||
|
||||
VStack(alignment: .leading) {
|
||||
Text(String(localized: "username")+"*")
|
||||
.default_text_style_700(styleSize: 15)
|
||||
.padding(.bottom, -5)
|
||||
|
||||
TextField("username", text : $accountLoginViewModel.username)
|
||||
.default_text_style(styleSize: 15)
|
||||
.disabled(coreContext.loggedIn)
|
||||
.frame(height: 25)
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 15)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(isNameFocused ? Color.orange_main_500 : Color.gray_200, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom)
|
||||
.focused($isNameFocused)
|
||||
|
||||
Text(String(localized: "password")+"*")
|
||||
.default_text_style_700(styleSize: 15)
|
||||
.padding(.bottom, -5)
|
||||
|
||||
ZStack(alignment: .trailing) {
|
||||
Group {
|
||||
if isSecured {
|
||||
SecureField("password", text: $accountLoginViewModel.passwd)
|
||||
.default_text_style(styleSize: 15)
|
||||
.frame(height: 25)
|
||||
.focused($isPasswordFocused)
|
||||
} else {
|
||||
TextField("password", text: $accountLoginViewModel.passwd)
|
||||
.default_text_style(styleSize: 15)
|
||||
.frame(height: 25)
|
||||
.focused($isPasswordFocused)
|
||||
}
|
||||
}
|
||||
Button(action: {
|
||||
isSecured.toggle()
|
||||
}) {
|
||||
Image(self.isSecured ? "eye-slash" : "eye")
|
||||
.renderingMode(.template)
|
||||
.resizable()
|
||||
.foregroundStyle(Color.gray_main2_500)
|
||||
.frame(width: 20, height: 20)
|
||||
}
|
||||
}
|
||||
.disabled(coreContext.loggedIn)
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 15)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(isPasswordFocused ? Color.orange_main_500 : Color.gray_200, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom)
|
||||
|
||||
Button(action: {
|
||||
if (self.coreContext.loggedIn){
|
||||
self.accountLoginViewModel.unregister()
|
||||
self.accountLoginViewModel.delete()
|
||||
} else {
|
||||
self.accountLoginViewModel.login()
|
||||
}
|
||||
}) {
|
||||
Text(coreContext.loggedIn ? "Log out" : "assistant_account_login")
|
||||
.default_text_style_white_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.background((accountLoginViewModel.username.isEmpty || accountLoginViewModel.passwd.isEmpty) ? Color.orange_main_100 : Color.orange_main_500)
|
||||
.cornerRadius(60)
|
||||
.disabled(accountLoginViewModel.username.isEmpty || accountLoginViewModel.passwd.isEmpty)
|
||||
.padding(.bottom)
|
||||
|
||||
Button(action: {
|
||||
|
||||
}) {
|
||||
Text("Forgotten password?")
|
||||
.underline()
|
||||
.default_text_style_600(styleSize: 15)
|
||||
.foregroundStyle(Color.gray_main2_500)
|
||||
}
|
||||
.frame(maxWidth: .infinity)
|
||||
.padding(.bottom, 30)
|
||||
|
||||
HStack {
|
||||
VStack{
|
||||
Divider()
|
||||
}
|
||||
Text(" or ")
|
||||
.default_text_style(styleSize: 15)
|
||||
.foregroundStyle(Color.gray_main2_500)
|
||||
VStack{
|
||||
Divider()
|
||||
}
|
||||
}
|
||||
.padding(.bottom, 10)
|
||||
|
||||
Button(action: {
|
||||
|
||||
}) {
|
||||
HStack {
|
||||
Image("qr-code")
|
||||
.renderingMode(.template)
|
||||
.resizable()
|
||||
.foregroundStyle(Color.orange_main_500)
|
||||
.frame(width: 20, height: 20)
|
||||
|
||||
Text("Scan QR code")
|
||||
.default_text_style_orange_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
}
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(Color.orange_main_500, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom)
|
||||
|
||||
Button(action: {
|
||||
|
||||
}) {
|
||||
Text("Use SIP Account")
|
||||
.default_text_style_orange_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(Color.orange_main_500, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom)
|
||||
|
||||
HStack(alignment: .center) {
|
||||
|
||||
Spacer()
|
||||
|
||||
Text("Not account yet?")
|
||||
.default_text_style(styleSize: 15)
|
||||
.foregroundStyle(Color.gray_main2_700)
|
||||
.padding(.horizontal, 10)
|
||||
|
||||
Button(action: {
|
||||
|
||||
}) {
|
||||
Text("Register")
|
||||
.default_text_style_orange_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(Color.orange_main_500, lineWidth: 1)
|
||||
)
|
||||
.padding(.horizontal, 10)
|
||||
|
||||
Spacer()
|
||||
}
|
||||
.padding(.bottom)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#Preview {
|
||||
LoginFragment(accountLoginViewModel: AccountLoginViewModel())
|
||||
}
|
||||
129
Linphone/UI/Assistant/Fragments/ProfileModeFragment.swift
Normal file
129
Linphone/UI/Assistant/Fragments/ProfileModeFragment.swift
Normal file
|
|
@ -0,0 +1,129 @@
|
|||
/*
|
||||
* Copyright (c) 2010-2023 Belledonne Communications SARL.
|
||||
*
|
||||
* This file is part of linphone-iphone
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import SwiftUI
|
||||
|
||||
struct ProfileModeFragment: View {
|
||||
|
||||
@State var options: Int = 1
|
||||
@State private var isShowPopup = false
|
||||
@State private var isShowPopupForDefault = true
|
||||
|
||||
var body: some View {
|
||||
GeometryReader { geometry in
|
||||
ScrollView(.vertical) {
|
||||
VStack {
|
||||
ZStack {
|
||||
Image("mountain")
|
||||
.resizable()
|
||||
.scaledToFill()
|
||||
.frame(width: geometry.size.width, height: 100)
|
||||
.clipped()
|
||||
Text("assistant_account_login")
|
||||
.default_text_style_white_800(styleSize: 20)
|
||||
.padding(.top, 20)
|
||||
}
|
||||
.padding(.top, 35)
|
||||
.padding(.bottom, 10)
|
||||
|
||||
VStack (spacing: 10) {
|
||||
Button(action: {
|
||||
options = 1
|
||||
}) {
|
||||
HStack {
|
||||
Image(options == 1 ? "radio-button-fill" : "radio-button")
|
||||
Text("Default")
|
||||
.profile_mode_text_style_gray_800(styleSize: 16)
|
||||
Image("info")
|
||||
.resizable()
|
||||
.frame(width: 25, height: 25)
|
||||
.onTapGesture {
|
||||
withAnimation {
|
||||
self.isShowPopupForDefault = true
|
||||
self.isShowPopup.toggle()
|
||||
}
|
||||
}
|
||||
Spacer()
|
||||
}
|
||||
}
|
||||
|
||||
HStack {
|
||||
Text("Chiffrement de bout en bout de tous vos échanges, grâce au mode default vos communications sont à l’abri des regards.")
|
||||
.profile_mode_text_style_gray(styleSize: 15)
|
||||
}
|
||||
.frame(maxWidth: .infinity, alignment: .leading)
|
||||
.padding(.horizontal, 16)
|
||||
.padding(.vertical, 20)
|
||||
.background(Color.gray_100)
|
||||
.cornerRadius(15)
|
||||
.padding(.bottom, 5)
|
||||
|
||||
Image("profile-mode")
|
||||
.resizable()
|
||||
.frame(width: 150, height: 60)
|
||||
.padding()
|
||||
|
||||
Button(action: {
|
||||
options = 2
|
||||
}) {
|
||||
HStack {
|
||||
Image(options == 2 ? "radio-button-fill" : "radio-button")
|
||||
Text("Interoperable")
|
||||
.profile_mode_text_style_gray_800(styleSize: 16)
|
||||
Image("info")
|
||||
.resizable()
|
||||
.frame(width: 25, height: 25)
|
||||
.onTapGesture {
|
||||
withAnimation {
|
||||
self.isShowPopupForDefault = false
|
||||
self.isShowPopup.toggle()
|
||||
}
|
||||
}
|
||||
Spacer()
|
||||
}
|
||||
}
|
||||
|
||||
HStack {
|
||||
Text("Ce mode vous permet d’être interopérable avec d’autres services SIP.\nVos communications seront chiffrées de point à point. ")
|
||||
.profile_mode_text_style_gray(styleSize: 15)
|
||||
}
|
||||
.frame(maxWidth: .infinity, alignment: .leading)
|
||||
.padding(.horizontal, 16)
|
||||
.padding(.vertical, 20)
|
||||
.background(Color.gray_100)
|
||||
.cornerRadius(15)
|
||||
}
|
||||
.padding()
|
||||
}
|
||||
}
|
||||
if self.isShowPopup {
|
||||
PopupView(isShowPopup: $isShowPopup, title: Text(isShowPopupForDefault ? "Default mode" : "Interoperable mode"), content: Text(isShowPopupForDefault ? "Texte explicatif du default mode : lorem ipsum dolor sit amet, consectetur adipiscing elit. Etiam velit sapien, egestas sit amet dictum eget, condimentum a ligula." : "Texte explicatif du interoperable mode : lorem ipsum dolor sit amet, consectetur adipiscing elit. Etiam velit sapien, egestas sit amet dictum eget, condimentum a ligula."), titleFirstButton: nil, actionFirstButton: {}, titleSecondButton: Text("Close"), actionSecondButton: {self.isShowPopup.toggle()})
|
||||
.background(.black.opacity(0.65))
|
||||
.edgesIgnoringSafeArea(.all)
|
||||
.onTapGesture {
|
||||
self.isShowPopup.toggle()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#Preview {
|
||||
ProfileModeFragment()
|
||||
}
|
||||
|
|
@ -28,7 +28,7 @@ struct ContentView: View {
|
|||
if UserDefaults.standard.bool(forKey: "general_terms") == false {
|
||||
WelcomeView(sharedMainViewModel: sharedMainViewModel)
|
||||
} else if coreContext.mCore.defaultAccount == nil {
|
||||
AssistantView(accountLoginViewModel: AccountLoginViewModel())
|
||||
AssistantView()
|
||||
} else {
|
||||
TabView {
|
||||
ContactsView()
|
||||
|
|
|
|||
|
|
@ -25,49 +25,62 @@ struct PopupView: View {
|
|||
var permissionManager = PermissionManager.shared
|
||||
|
||||
@Binding var isShowPopup: Bool
|
||||
var title: Text
|
||||
var content: Text
|
||||
|
||||
var titleFirstButton: Text?
|
||||
var actionFirstButton: () -> ()
|
||||
|
||||
var titleSecondButton: Text?
|
||||
var actionSecondButton: () -> ()
|
||||
|
||||
var body: some View {
|
||||
GeometryReader { geometry in
|
||||
VStack (alignment: .leading) {
|
||||
Text("Conditions de service")
|
||||
title
|
||||
.default_text_style_800(styleSize: 16)
|
||||
.frame(alignment: .leading)
|
||||
.padding(.bottom, 2)
|
||||
|
||||
Text("En continuant, vous acceptez ces conditions, \(Text("[notre politique de confidentialité](https://linphone.org/privacy-policy)").underline()) et \(Text("[nos conditions d’utilisation](https://linphone.org/general-terms)").underline()).")
|
||||
.tint(Color.gray_main2_600)
|
||||
content
|
||||
.tint(Color.gray_main2_600)
|
||||
.default_text_style(styleSize: 15)
|
||||
.padding(.bottom, 20)
|
||||
|
||||
Button(action: {
|
||||
self.isShowPopup.toggle()
|
||||
}) {
|
||||
Text("Deny all")
|
||||
.default_text_style_orange_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(Color.orange_main_500, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom, 10)
|
||||
Button(action: {
|
||||
permissionManager.photoLibraryRequestPermission()
|
||||
}) {
|
||||
Text("Accept all")
|
||||
.default_text_style_white_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.background(Color.orange_main_500)
|
||||
.cornerRadius(60)
|
||||
if titleFirstButton != nil {
|
||||
Button(action: {
|
||||
actionFirstButton()
|
||||
}) {
|
||||
titleFirstButton
|
||||
.default_text_style_orange_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.cornerRadius(60)
|
||||
.overlay(
|
||||
RoundedRectangle(cornerRadius: 60)
|
||||
.inset(by: 0.5)
|
||||
.stroke(Color.orange_main_500, lineWidth: 1)
|
||||
)
|
||||
.padding(.bottom, 10)
|
||||
}
|
||||
|
||||
if titleSecondButton != nil {
|
||||
Button(action: {
|
||||
actionSecondButton()
|
||||
}) {
|
||||
titleSecondButton
|
||||
.default_text_style_white_600(styleSize: 20)
|
||||
.frame(height: 35)
|
||||
.frame(maxWidth: .infinity)
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 10)
|
||||
.background(Color.orange_main_500)
|
||||
.cornerRadius(60)
|
||||
}
|
||||
}
|
||||
.padding(.horizontal, 20)
|
||||
.padding(.vertical, 20)
|
||||
|
|
@ -79,3 +92,7 @@ struct PopupView: View {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
#Preview {
|
||||
PopupView(isShowPopup: .constant(true), title: Text("Title"), content: Text("Content"), titleFirstButton: Text("Deny all"), actionFirstButton: {}, titleSecondButton: Text("Accept all"), actionSecondButton: {})
|
||||
}
|
||||
|
|
|
|||
|
|
@ -112,7 +112,7 @@ struct WelcomeView: View{
|
|||
}
|
||||
|
||||
if self.isShowPopup {
|
||||
PopupView(isShowPopup: $isShowPopup)
|
||||
PopupView(isShowPopup: $isShowPopup, title: Text("Conditions de service"), content: Text("En continuant, vous acceptez ces conditions, \(Text("[notre politique de confidentialité](https://linphone.org/privacy-policy)").underline()) et \(Text("[nos conditions d’utilisation](https://linphone.org/general-terms)").underline())."), titleFirstButton: Text("Deny all"), actionFirstButton: {self.isShowPopup.toggle()}, titleSecondButton: Text("Accept all"), actionSecondButton: {permissionManager.photoLibraryRequestPermission()})
|
||||
.background(.black.opacity(0.65))
|
||||
.edgesIgnoringSafeArea(.all)
|
||||
.onTapGesture {
|
||||
|
|
|
|||
|
|
@ -126,4 +126,14 @@ extension View {
|
|||
self.font(Font.custom("NotoSans-Regular", size: styleSize))
|
||||
.foregroundStyle(Color.gray_main2_600)
|
||||
}
|
||||
|
||||
func profile_mode_text_style_gray_800(styleSize: CGFloat) -> some View {
|
||||
self.font(Font.custom("NotoSans-ExtraBold", size: styleSize))
|
||||
.foregroundStyle(Color.gray_900)
|
||||
}
|
||||
|
||||
func profile_mode_text_style_gray(styleSize: CGFloat) -> some View {
|
||||
self.font(Font.custom("NotoSans-Regular", size: styleSize))
|
||||
.foregroundStyle(Color.gray_main2_600)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue