- Published on
Discovering Possibilities with MapKit
- Authors
- Name
- Rosa Tiara
For those of us who enjoy documenting our travel experiences but prefer to keep our notes and reviews private, sharing them on a public review platform can feel uncomfortable. That’s why I built MemoSpot — an iOS app that allows you to document your personal notes regarding the places you’ve visited, serving as a private journal for you!
Tools & Frameworks
-
SwiftUI: a framework by Apple, used to create MemoSpot’s user interface.
-
MapKit: to provide accurate and interactive maps. It enables users to view their visited places, mark specific locations, and navigate through their place history seamlessly.
-
CoreLocation: to allow users to record their exact coordinates with precise positioning and location tracking.
-
CoreData: database system to store and manage user’s data.
The Process
Research / Investigation
1) Ask questions
They said *curiosity kills the cat, *but in this part, I literally had to kill the cat. We needed to embrace curiosity fully, even if it means questioning everything. Since my topic is about Location framework (CoreLocation & MapKit), these are some of the questions that I asked:
-
How does digital map affect our daily lives?
-
Why do people want to use my app? Who are my target audience?
-
How does the Location framework handle location updates and changes in real-time?
-
Does the Location framework support reverse geocoding? How can we use it?
2) Seek for answers
After I’m done with my questions, I organized related questions into groups and addressed them. I did some research by surfing on the internet, asking mentors, and reached out to my peers.
3) Synthesize
At this stage, I gather all the findings I’ve discovered, and that led me to the final section, App Statement. These are the findings:
-
Digital maps provide real-time navigation, allows us to search for a way to specific location, provide info about public transportations, etc.
-
The people I want to reach are those who want to write down their experiences of places they’ve been to, but they only want to keep it to themselves. They want to use MemoSpot because it prioritizes privacy.
-
Location handles real-time updates by using continuous location monitoring, region monitoring, and significant location change monitoring.
-
Yep, it does! We can use it with geocoder.reverseGeocodeLocation() method.
4) Make an app statement
This is my app statement:
An app that can store notes and keep track of visited places for travelers. This is a solution because some people may not be comfortable sharing their experiences publicly with platform like other platforms.
Format:
An app that (the main purpose of the app) for (main target user) when (user’s condition) by (a synthetic description of what the app does). This is a solution to the challenge because (explain your solution briefly).
Design
Here’s my app design. I followed Apple’s Map layout with the search bar at the bottom. My mentor also assisted in choosing the right color combinations for the app.
App flow: Users begin by searching for either visited or desired destinations. Once a place is selected, they can add personalized notes. The note is automatically saved when the “Save Note” button is clicked. To see the saved note, the user simply has to tap on the red annotation.
Development (Coding)
The coding process was divided into two main parts:
- Making the UI
During this stage, I focused on creating the visual appearance of my app without adding any functionality. This involved designing the map display using MapKit, showing the user’s current location with CoreLocation, and adding buttons that don’t have any interactive actions yet. The aim was to establish a visually appealing and user-friendly interface as a starting point for the app’s functionality.
- Adding functionality & connect with Core Data
Once I've implemented all the features and functionalities, it’s important to ensure that the data added by the user, including the selected place, note, and annotation, is saved locally. To achieve this, I incorporated an entity called PlaceEntity
into my project's Core Data. Then I created a custom CoreDataViewModel that handles all the necessary functionalities related to Core Data.
CoreDataViewModel.swift 🖥️
class CoreDataViewModel: ObservableObject {
@Published var placeList: [PlaceEntity] = []
let manager = PersistenceController.shared
func fetchPlaces() {
let request: NSFetchRequest<PlaceEntity> = PlaceEntity.fetchRequest()
do {
placeList = try manager.container.viewContext.fetch(request)
} catch let error {
print(error.localizedDescription)
}
print(placeList)
}
func isDataEmpty() -> Bool {
return placeList.isEmpty
}
func saveNote(longitude: Double, latitude: Double, placeName: String, placeNote: String) {
if !placeNote.isEmpty {
let newNote = PlaceEntity(context: manager.container.viewContext)
newNote.latitude = latitude
newNote.longitude = longitude
newNote.placeName = placeName
newNote.placeNote = placeNote
//add annotation
let mapViewModel = MapViewModel()
mapViewModel.addAnnotationMarker(latitude: latitude, longitude: longitude, title: placeName)
saveChanges()
placeList.append(newNote)
}
}
private func saveChanges() {
do {
try manager.container.viewContext.save()
} catch {
print(error.localizedDescription)
}
}
}
-
fetchPlaces()
: fetches saved places from PlaceEntity using NSFetchRequest. -
isDataEmtpy()
: checks whether the data is empty or not -
saveNote()
: saves note with it’s selected coordinate (longitude, latitude), current place name, and the corresponding note added by user. -
saveChanges()
: saves the data to PersistenceController. It is set as private so no other class outside can access it.
Worry not, the full code is provided at the end of this article :)
The Problems & How I Dealt with It
When I first found out that I needed to use the Location framework in my application, I felt worried. I had never used that framework before and didn’t know much about it. I didn’t feel very confident at first, but I knew deep down that I could figure it out. Luckily, I had mentors and friends who were always there to help me when I needed it.
For the technical part, it took me some time to carefully read the Apple's documentation about CoreLocation. During that time, I attended a session with my mentor where they taught me how to properly read technical documentation. I gained a lot of knowledge from it and realized that I had been doing it wrong before. But that’s okay, I’m happy that I learned from it! ;)
Things I Learned
- Step out of my comfort zone
Sticking to my comfort zone may feel easy and safe, but it won’t take me so far. I’m grateful for the challenge I received because it pushed me to get outside my comfort zone, which helped me grow and improve my programming skills. It felt uncomfortable at first, but once I got involved, I developed a passion for the process.
- Asking the right questions
Asking the right question, especially when dealing with a problem, requires a particular skill. This is the framework I follow:
- State your goal.
- Describe the problem you’re facing.
- Explain what you’ve tried so far.
- Mention what’s working and what’s not.
Example:
🔎 Goal: I attempted to add my placeList to PlaceEntity.
🤔 Problem: However, when I print the placeList to my terminal, all the values are null, indicating that my code isn’t fetching the newly added places correctly.
🙀 What I’ve tried: I searched for solutions on Stack Overflow, and it seems that the issue might be related to the fetching process in Core Data. Can you assist me in resolving this?
- Focus management
As I work on this project alone, I took care of all the tasks, from planning to coding. I believe that managing my focus is more important than managing my time because staying concentrated can be challenging but is vital for being productive. When I effectively manage my focus and have clear goals, I find it easier to tackle tasks.
Thank you for taking the time to read! :)