Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions Runnect-iOS/Runnect-iOS.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@
CE17F0352961BEF800E1DED0 /* Pretendard-SemiBold.otf in Resources */ = {isa = PBXBuildFile; fileRef = CE17F0312961BEF800E1DED0 /* Pretendard-SemiBold.otf */; };
CE17F0362961BEF800E1DED0 /* Pretendard-Regular.otf in Resources */ = {isa = PBXBuildFile; fileRef = CE17F0322961BEF800E1DED0 /* Pretendard-Regular.otf */; };
CE17F0382961BF8B00E1DED0 /* FontLiterals.swift in Sources */ = {isa = PBXBuildFile; fileRef = CE17F0372961BF8B00E1DED0 /* FontLiterals.swift */; };
CE29D582296402B500F47542 /* CourseDrawingVC.swift in Sources */ = {isa = PBXBuildFile; fileRef = CE29D581296402B500F47542 /* CourseDrawingVC.swift */; };
CE29D584296416D800F47542 /* caculateStatusBarHeight.swift in Sources */ = {isa = PBXBuildFile; fileRef = CE29D583296416D800F47542 /* caculateStatusBarHeight.swift */; };
CE4545C9295D7AF4003201E1 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = CE4545C8295D7AF4003201E1 /* AppDelegate.swift */; };
CE4545CB295D7AF4003201E1 /* SceneDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = CE4545CA295D7AF4003201E1 /* SceneDelegate.swift */; };
CE4545CD295D7AF4003201E1 /* TaBarController.swift in Sources */ = {isa = PBXBuildFile; fileRef = CE4545CC295D7AF4003201E1 /* TaBarController.swift */; };
Expand Down Expand Up @@ -102,6 +104,8 @@
CE17F0312961BEF800E1DED0 /* Pretendard-SemiBold.otf */ = {isa = PBXFileReference; lastKnownFileType = file; path = "Pretendard-SemiBold.otf"; sourceTree = "<group>"; };
CE17F0322961BEF800E1DED0 /* Pretendard-Regular.otf */ = {isa = PBXFileReference; lastKnownFileType = file; path = "Pretendard-Regular.otf"; sourceTree = "<group>"; };
CE17F0372961BF8B00E1DED0 /* FontLiterals.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FontLiterals.swift; sourceTree = "<group>"; };
CE29D581296402B500F47542 /* CourseDrawingVC.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CourseDrawingVC.swift; sourceTree = "<group>"; };
CE29D583296416D800F47542 /* caculateStatusBarHeight.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = caculateStatusBarHeight.swift; sourceTree = "<group>"; };
CE4545C5295D7AF4003201E1 /* Runnect-iOS.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = "Runnect-iOS.app"; sourceTree = BUILT_PRODUCTS_DIR; };
CE4545C8295D7AF4003201E1 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
CE4545CA295D7AF4003201E1 /* SceneDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SceneDelegate.swift; sourceTree = "<group>"; };
Expand Down Expand Up @@ -308,6 +312,7 @@
children = (
CEEC6B392961C4F300D00E1E /* CourseDrawingHomeVC.swift */,
CEC2A6912962BE2900160BF7 /* DepartureSearchVC.swift */,
CE29D581296402B500F47542 /* CourseDrawingVC.swift */,
CEB8416F2963360800BF8080 /* CountDownVC.swift */,
);
path = VC;
Expand Down Expand Up @@ -527,6 +532,7 @@
CE58759F29601500005D967E /* Toast.swift */,
CE6655C9295D84DD00C64E12 /* UserDefaultKeyList.swift */,
CEC2A68F2962B06C00160BF7 /* convertLocationObject.swift */,
CE29D583296416D800F47542 /* caculateStatusBarHeight.swift */,
);
path = Utils;
sourceTree = "<group>";
Expand Down Expand Up @@ -821,6 +827,7 @@
CE6655F4295D898400C64E12 /* UIViewController+.swift in Sources */,
CE5645162961B72E000A2856 /* ImageLiterals.swift in Sources */,
CE6655CD295D856300C64E12 /* KeyPathFindable.swift in Sources */,
CE29D582296402B500F47542 /* CourseDrawingVC.swift in Sources */,
CE6655E4295D884600C64E12 /* UILabel+.swift in Sources */,
CE6655FA295D90E000C64E12 /* applyShadow.swift in Sources */,
A3BC2F2B2962C3D500198261 /* GoalRewardInfoVC.swift in Sources */,
Expand Down Expand Up @@ -855,6 +862,7 @@
CEEC6B3A2961C4F300D00E1E /* CourseDrawingHomeVC.swift in Sources */,
CEC2A6902962B06C00160BF7 /* convertLocationObject.swift in Sources */,
CEC2A6852961F92C00160BF7 /* CustomButton.swift in Sources */,
CE29D584296416D800F47542 /* caculateStatusBarHeight.swift in Sources */,
CE66560C295D928300C64E12 /* setRootViewController.swift in Sources */,
CE6655D9295D871B00C64E12 /* URL+.swift in Sources */,
CE6655DE295D877F00C64E12 /* UIColor+.swift in Sources */,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -107,11 +107,24 @@ extension CustomNavigationBar {
return self
}

@discardableResult
func setTextFieldText(text: String) -> Self {
self.textField.text = text
self.textField.isUserInteractionEnabled = false
return self
}

@discardableResult
func showKeyboard() -> Self {
self.textField.becomeFirstResponder()
return self
}

@discardableResult
func hideRightButton() -> Self {
self.rightButton.isHidden = true
return self
}
}

// MARK: - @objc Function
Expand Down
74 changes: 37 additions & 37 deletions Runnect-iOS/Runnect-iOS/Global/UIComponents/MapView/RNMapView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -17,15 +17,17 @@ final class RNMapView: UIView {
// MARK: - Properties

@Published var pathDistance: Double = 0
@Published var markerCount = 0

let pathImage = PassthroughSubject<UIImage, Never>()
var cancelBag = Set<AnyCancellable>()

let locationManager = CLLocationManager()
private var isDrawMode: Bool = false
private var markers = [RNMarker]() {
didSet {
markerCount = markers.count + 1
self.makePath()
self.setUndoButton()
}
}
/// startMarker를 포함한 모든 마커들의 위치 정보
Expand All @@ -40,7 +42,6 @@ final class RNMapView: UIView {
private var startMarker = RNStartMarker()
private let pathOverlay = NMFPath()
private let locationButton = UIButton(type: .custom)
private let undoButton = UIButton(type: .custom)

// MARK: - initialization

Expand Down Expand Up @@ -89,19 +90,25 @@ extension RNMapView {

/// 지정 위치에 startMarker와 출발 infoWindow 생성 (기존의 startMarker는 제거)
@discardableResult
func makeStartMarker(at location: NMGLatLng) -> Self {
func makeStartMarker(at location: NMGLatLng, withCameraMove: Bool = false) -> Self {
self.startMarker.position = location
self.startMarker.mapView = self.map.mapView
self.startMarker.showInfoWindow()
if withCameraMove {
moveToLocation(location: location)
}
markerCount = 1
return self
}

/// 사용자 위치에 startMarker와 출발 infoWindow 생성 (기존의 startMarker는 제거)
@discardableResult
func makeStartMarkerAtUserLocation() -> Self {
func makeStartMarkerAtUserLocation(withCameraMove: Bool = false) -> Self {
self.startMarker.position = getUserLocation()
self.startMarker.mapView = self.map.mapView
self.startMarker.showInfoWindow()
moveToUserLocation()
markerCount = 1
return self
}

Expand Down Expand Up @@ -149,6 +156,18 @@ extension RNMapView {
return self
}

/// 지정 위치로 카메라 이동
@discardableResult
func moveToLocation(location: NMGLatLng) -> Self {
let cameraUpdate = NMFCameraUpdate(scrollTo: location)

DispatchQueue.main.async { [self] in
cameraUpdate.animation = .easeIn
self.map.mapView.moveCamera(cameraUpdate)
}
return self
}

/// 저장된 위치들로 경로선 그리기
@discardableResult
func makePath() -> Self {
Expand All @@ -168,13 +187,6 @@ extension RNMapView {
return self
}

/// undoButton 설정
@discardableResult
func showUndoButton(toShow: Bool) -> Self {
self.undoButton.isHidden = !toShow
return self
}

/// 지도에 ContentPadding을 지정하여 중심 위치가 변경되게 설정
@discardableResult
func makeContentPadding(padding: UIEdgeInsets) -> Self {
Expand Down Expand Up @@ -217,7 +229,7 @@ extension RNMapView {
}
}

// 바운더리(MBR) 생성
/// 바운더리(MBR) 생성
func makeMBR() -> NMGLatLngBounds {
var latitudes = [Double]()
var longitudes = [Double]()
Expand All @@ -231,6 +243,13 @@ extension RNMapView {
return NMGLatLngBounds(southWest: southWest, northEast: northEast)
}

/// 직전의 마커 생성을 취소하고 경로선도 제거
func undo() {
guard let lastMarker = self.markers.popLast() else { return }
substractDistance(with: lastMarker.position)
lastMarker.mapView = nil
}

// 두 지점 사이의 거리(m) 추가
private func addDistance(with newLocation: NMGLatLng) {
let lastCLLoc = markersLatLngs.last?.toCLLocation()
Expand All @@ -254,7 +273,7 @@ extension RNMapView {
map.showLocationButton = false
map.showScaleBar = false

map.mapView.logoAlign = .leftTop
map.mapView.logoAlign = .rightTop
}

private func getLocationAuth() {
Expand All @@ -278,13 +297,9 @@ extension RNMapView {
}

private func setPathOverlay() {
pathOverlay.width = 3
pathOverlay.width = 4
pathOverlay.outlineWidth = 0
pathOverlay.color = .purple
}

private func setUndoButton() {
self.undoButton.isEnabled = (markers.count >= 1)
pathOverlay.color = .m1
}
}

Expand All @@ -296,14 +311,10 @@ extension RNMapView {
self.locationButton.setImage(ImageLiterals.icMapLocation, for: .normal)
self.locationButton.isHidden = true
self.locationButton.addTarget(self, action: #selector(locationButtonDidTap), for: .touchUpInside)

self.undoButton.setImage(ImageLiterals.icCancel, for: .normal)
self.undoButton.isHidden = true
self.undoButton.addTarget(self, action: #selector(undoButtonDidTap), for: .touchUpInside)
}

private func setLayout() {
addSubviews(map, locationButton, undoButton)
addSubviews(map, locationButton)

map.snp.makeConstraints { make in
make.edges.equalToSuperview()
Expand All @@ -313,15 +324,10 @@ extension RNMapView {
make.bottom.equalToSuperview().inset(98+bottomPadding)
make.trailing.equalToSuperview().inset(24)
}

undoButton.snp.makeConstraints { make in
make.bottom.equalToSuperview().inset(98+bottomPadding)
make.trailing.equalToSuperview().inset(24)
}
}

private func updateSubviewsConstraints() {
[locationButton, undoButton].forEach { view in
[locationButton].forEach { view in
view.snp.updateConstraints { make in
make.bottom.equalToSuperview().inset(98+bottomPadding)
}
Expand All @@ -335,20 +341,14 @@ extension RNMapView {
@objc func locationButtonDidTap() {
self.setPositionMode(mode: .direction)
}

@objc func undoButtonDidTap() {
guard let lastMarker = self.markers.popLast() else { return }
substractDistance(with: lastMarker.position)
lastMarker.mapView = nil
}
}

// MARK: - NMFMapViewCameraDelegate, NMFMapViewTouchDelegate

extension RNMapView: NMFMapViewCameraDelegate, NMFMapViewTouchDelegate {
// 지도 탭 이벤트
func mapView(_ mapView: NMFMapView, didTapMap latlng: NMGLatLng, point: CGPoint) {
guard isDrawMode else { return }
guard isDrawMode && markers.count < 19 else { return }
self.makeMarker(at: latlng)
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ extension RNStartMarker: NMFOverlayImageDataSource {
func view(with overlay: NMFOverlay) -> UIView {
// 마커 위에 보여줄 InfoView 이미지 리턴
let imageView = UIImageView(frame: CGRect(x: 0, y: 0, width: 58, height: 34))
imageView.image = ImageLiterals.icMapDeparture
imageView.image = ImageLiterals.icMapStart
return imageView
}
}
25 changes: 25 additions & 0 deletions Runnect-iOS/Runnect-iOS/Global/Utils/caculateStatusBarHeight.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
//
// caculateStatusBarHeight.swift
// Runnect-iOS
//
// Created by sejin on 2023/01/03.
//

import UIKit

extension UIApplication {
var statusBarHeight: CGFloat {
connectedScenes
.compactMap {
$0 as? UIWindowScene
}
.compactMap {
$0.statusBarManager
}
.map {
$0.statusBarFrame
}
.map(\.height)
.max() ?? 0
}
}
Loading