Professional Documents
Culture Documents
224 Lab Manual - Pages
224 Lab Manual - Pages
Lab Manual
Winter 2020
Michael Horie
Camosun College
ICS 224 Lab Manual
Page 2 of 56
ICS 224 Lab Manual
4. Profiling an App 19
5. Completion 19
Lab 4: Creating a Master-Detail App 21
Goals 21
Preparation 21
1. Setting up Source Control the Second Time 21
2. Creating a Model 22
3. Creating a Detail View 22
4. Adding a Default Image 23
5. Adapting the Master View 24
6. Creating a Custom Table View Cell 25
7. Completion 25
Lab 5: Refining the Master-Detail App 26
Goals 26
Preparation 26
1. Handling UITextViewDelegate Events 26
2. Adding Persistence (Load/Save) 26
3. Using ScrollViews 29
4. Completion 30
Lab 6: Adding Photo Support 31
Page 3 of 56
ICS 224 Lab Manual
Goals 31
Preparation 31
1. Adding Camera Access 31
2. Adding Photo Library Access via a Gesture Recognizer 33
3. Adding Date Support 34
4. Completion 34
Lab 7: Documents and Segues 35
Goals 35
Preparation 35
1. Creating a Document-Based App 35
2. Setting up Segues 37
3. Completion 39
Lab 8: A First Look at ARKit 40
Goals 40
Preparation 40
1. Setting up the Project 40
2. Exploring the Project 40
3. Adding an Object 41
4. Adding Behaviour 41
5. Adding Notifications 42
Page 4 of 56
ICS 224 Lab Manual
6. Completion 42
Lab 9: Surface Detection and Physics 43
Goals 43
Preparation 43
1. Setting up the Project 43
2. Exploring the Project 43
3. Adding a Scene Asset 43
4. Monitoring AR Session Management 44
5. Positioning an Asset 45
6. Adding Physics 46
7. Detecting Surfaces 48
8. Completion 49
Lab 10: Challenge Lab 50
Goals 50
Preparation 50
1. Creating the App 50
2. Completion 50
Appendix A: Code Marking Scheme 51
Appendix B: Xcode Icons 53
Top Panel (Left) 54
Page 5 of 56
ICS 224 Lab Manual
Page 6 of 56
ICS 224 Lab Manual
Preparation
If you do not already have Gitlab credentials from ICS 199, create an account on Bitbucket or GitHub using your generic ICS
credentials
If you are using GitHub, but have not yet set up a personal access token, log in to GitHub, go to Settings > Developer
settings > Personal access tokens, and generate a repo token for Xcode (enter Xcode in the Note field and select repo (all
related rights should remain selected). Be sure to record this token; you will need it below
Log in to your Mac
Click on the magnifying glass in the top right corner
Enter Xcode
Launch Xcode
Right-click on the Xcode icon that appeared in the Dock at the bottom of the screen, then select Options > Keep in Dock. This
bookmarks Xcode, making it easier to find next time
Page 7 of 56
ICS 224 Lab Manual
Page 8 of 56
ICS 224 Lab Manual
Info.plist: Contains information about the app, such as the version, what the iOS device needs to provide (e.g., GPS), what
private information is used, and which orientations (landscape, portrait) are supported
Click on Main.storyboard
From the menu, make sure Editor > Canvas > Bounds Rectangles is selected, to
make it easy to detect UI elements that have transparent backgrounds
Click on the Library button (see Appendix B)
Drag a Switch, a Button, and a Label onto the canvas, one at a time
Make the UI look as illustrated on the right. You can change the label of an
element by double-clicking on it. If elements are not quite centred, don't worry
about that for now
Run the app by clicking on the Play button (see Appendix B)
Be patient; the first launch will take some time!
Move the switch and push the button; they don't do anything useful because we
have not yet tied them to any actions
Stop the app by pressing the Stop button (see Appendix B)
Note the M (Modified) letter next to Main.storyboard
Go to Source Control > Commit and add a commit message (e.g., "Initial UI")
Select Push to remote
Page 9 of 56
ICS 224 Lab Manual
Page 10 of 56
ICS 224 Lab Manual
Add the following function to the increasePushCount function, to increase the value in countLabel every time the button is
pushed:
let currentCount = Int(countLabel.text!)
let nextCount = (currentCount ?? 0) + 1
countLabel.text = String(nextCount)
Run the program and confirm that the switch will enable/disable the button and that each button press will increment the current
count by 1. This program has an overflow issue, but don't worry about that for now
Be sure to commit and push the working code to the repository
Page 11 of 56
ICS 224 Lab Manual
Preparation
Section groups 1 and 2 are independent of each other; if you are stuck in one group waiting for support, continue to work on the
other group
Page 12 of 56
ICS 224 Lab Manual
orientations (in Xcode, to the right of the Play button, you can pick different devices, and in the
Simulator, the Hardware menu allows you to test different screen orientations)
Once the UI layout is working correctly, commit and push your changes
Click on the Count Button and click on the Add New Constraints button (see Appendix B)
Change the top spacing to 32
If you look closely, you will see that an error has occurred; to resolve it, first click on the white-on-red arrow to the right of the
View Controller Scene
Click on the white-on-red dot and delete the top constraint
Note that the error has been resolved; normally, the Count Button would have been moved
down by 32 points, but because the button is part of a Stack View, vertical spacing is
dictated by the Stack View itself. Constraints in this case must be changed as follows:
Click on the Stack View
Click on the Attributes Inspector button
Change the spacing to 32
Now right-click on the main storyboard and select Source Control > Discard Changes to return to
your most-recently committed version.
Change the layout of the initialValueTextField and the countLabel so that they take up the entire
space within the Stack View (see the circled portion on the right)
Click on the Attributes Inspector button to centre the text in the initialValueTextField and the countLabel
Run the app and keep pressing the button repeatedly, to make sure the numbers stay
centred Elements Centred and Full Length /0
Show the resulting layout to your instructor (Instructor Stamp)
Page 13 of 56
ICS 224 Lab Manual
Note that Appendix A will be applied, so be sure to structure your code well, check for errors, and document your
work
Commit and push all changes
3. Writing UI Tests
Click on the main storyboard
For each of the 4 elements:
Click on the element
Click on the Identity Inspector button (see Appendix B)
Enter the variable name of the element as the Identifier (e.g., the switch should be called countSwitch)
Click on the Project Navigator button
Click on Lab1UITests.swift
Click inside testExample()
Click on the red record button
Enter the number 10 and click on Push
Click on the record button again
Note that Xcode has added some code. Modify the code so that it looks like the following:
func test10() {
let app = XCUIApplication()
app.launch()
app.textFields["initialValueTextField"].tap()
app.buttons["countButton"].tap()
XCTAssertEqual(app.staticTexts["countLabel"].label, "11")
}
Now hover over the line to the left of func test10(). A white-on-black arrow should appear. Click on the arrow to launch the test
Make sure the test succeeds (a white-on-green checkmark should appear). If not, retrace all the steps of this Section
Add tests to check for various normal and abnormal cases. Be sure to achieve path coverage! In the process, also refactor
your test code so that it is easy to add new test cases, as well as easy to enter long sequences of digits. Avoid repetitive code
and note that Appendix A will be applied
Page 14 of 56
ICS 224 Lab Manual
Make sure the tests pass. You can run all UI tests in one go by clicking on the Test Navigator button (see Appendix B) and then
clicking on the white-on-gray arrow to the right of Lab1UITests
Show the result to your instructor.
After you have completed running your tests, your instructor will ask you to perform Automatic Tests Pass /0
some additional tests (Instructor Stamp)
Commit and push all changes
Print out a copy of your source code and your test code and attach it to this page. Src/Tst Code
/20
4. Completion
Log out of your Mac
Congratulations! You have completed this lab. Be sure to hand in this lab, along with your 2 (two) printouts, and see you
next week!
Page 15 of 56
ICS 224 Lab Manual
Preparation
Using your generic ICS credentials, go to https://appleid.apple.com and create an Apple ID
Obtain an iPad from your instructor at the beginning of the lab
1. Setting Breakpoints
Click on the Project Navigator button
Click on the ViewController.swift file
Make sure the Debug Area at the bottom of the screen is visible. If not, click on the Hide or Show the Debug Area button (See
Appendix B)
Page 16 of 56
ICS 224 Lab Manual
Click on the line number to the left of the first line of code underneath the increasePushCount function. For example, if
increasePushCount is on line 50, click on line 51 (assuming line 51 is not blank). A blue arrow should appear
Now run the app
Click the Push button
Xcode will be brought to the foreground and the execution of the app will stop at the breakpoint you just set
Click on the Step Over button (see Appendix B) to step to the next line
Keep watching the left side of the Debug Area and make sure the variables listed there are containing the values you expected
them to contain
Keep pressing the Step Over button until you get to the last line in the function
Press the Continue Program Execution button (see Appendix B)
Click the Push button again
Step through the function again, and make sure the variables are being updated correctly
From now on, if your app is not working correctly, step through the code first with the debugger and try to resolve the issue on
your own before contacting your instructor. Being able to troubleshoot code on your own is a crucial programming skill to hone!
Click on the Breakpoint Navigator button (see Appendix B)
A list of your breakpoints will appear. There should only be 1; click on it and press the Delete button to remove it
Page 17 of 56
ICS 224 Lab Manual
Page 18 of 56
ICS 224 Lab Manual
Memory: __________
Energy I.: __________
Disk: __________
Network: __________
It is a good idea to keep an eye on this; apps that consume too much of a resource are automatically terminated by iOS
Show the running app to your instructor
4. Profiling an App
In Xcode, click on Product > Build for Profiling
Click on Product > Profile
When the Instruments application has launched, select Time Profiler
Click on Choose
Click on the red Record button
Quickly push the Push button repeatedly and observe the resource usage; make sure it goes up when you press the button,
and then goes down when you don't interact with the app for a while
Note that because this app is simple, the system processes consume most of the resources
Stop the profiler
Change the app so that every time you press the Push button, the CountLabel is incremented by 1 for 10,000 times; this is of
course inefficient, but it will help to illustrate how profiling works
Run the program normally and make sure that it works
Build the project again for profiling and run it in Instruments as before
Quickly push the Push button repeatedly
After about 15 seconds of pushing repeatedly, click the Pause button in Instruments
You should see Lab1 at the top, with the highest Weight
In the right panel, the Heaviest Stack Trace should be listed
Double-click on the incrementPushCounter line; it should be the first black line underneath main (system calls are greyed out)
You should now see different counts, with the for loop receiving the highest count (counts are samples; they are not an accurate
count for efficiency reasons)
Show the result to your instructor Heavy Use Line Located /5
Next time your app is running sluggishly, or if it is consuming too much memory, use (Instructor Stamp)
Instruments to locate the source of the issue
Discard the changes; do not commit them
5. Completion
Log out of your Mac
Page 19 of 56
ICS 224 Lab Manual
Delete all photos and your app from the iPad, then return the iPad
Congratulations! You have completed this lab. Be sure to hand in this lab and see you next week!
Page 20 of 56
ICS 224 Lab Manual
Preparation
Obtain an iPad from your instructor at the beginning of the lab
Page 21 of 56
ICS 224 Lab Manual
Note that the basic functionality is already there: We can add items, click on items to view their details, and we can delete
items. Make sure you try out all these three actions
2. Creating a Model
Over the next few labs, we will create a travel notes app, allowing the user to take photos, add comments to them, and store this
information in an editable list.
Note that unlike the Single View App, there are two files, each representing a different view:
MasterViewController.swift contains code relevant to the master view
DetailViewController.swift contains code relevant to the detail view
Using just two classes for travel notes app will quickly result in a mess. For such (more complex) apps, an approach
resembling the Model-View-Controller pattern is preferable. To do that, we first need to create a model class. Click on File >
New > File
Select Swift File
Click on Next
Call the file PhotoEntry.swift
Click on Create
In the Project Navigator, drag the PhotoEntry.swift line into the Lab4 folder
Replace the code with the following:
import UIKit
// MARK: - Initializers
init(photo: UIImage, notes: String) {
self.photo = photo
self.notes = notes
}
}
Page 22 of 56
ICS 224 Lab Manual
Based on your work with constraints in Lab 2, group the Image and Text Views into a Stack View
Adjust the width of the Stack View such that its 4 borders touch the Safe Areas
Adjust the height so that the height of the Image and Text Views are the same. Do this by clicking on the Stack View,
selecting the Attributes Inspector, and then selecting Fill Equally for the Distribution
Make sure the UI displays correctly regardless of device and orientation (do not yet worry about anomalies introduced when the
keyboard appears). Don't forget to resolve layout errors, just like last time!
Remove all functions from DetailViewController.swift
Replace the code with the following:
import UIKit
// MARK: - Properties
@IBOutlet weak var photoView: UIImageView!
@IBOutlet weak var notesView: UITextView!
var entry: PhotoEntry?
Page 23 of 56
ICS 224 Lab Manual
Using the iPad camera, take a picture of yourself (or of your work station, if you prefer); don't take a picture of others without
their consent, especially since we will end up storing the photo on GitHub
Reconnect the iPad; the Photos application should come up
Import the photo
In Xcode, click on Assets.xcassets
Click on the +
Click on New Image Set
Drag the photo from Photos into the 3 blank frames
Rename the image in Xcode to defaultImage
Page 24 of 56
ICS 224 Lab Manual
7. Completion
Log out of your Mac
Delete all photos and your app from the iPad, then return the iPad
Congratulations! You have completed this lab. Be sure to hand in this lab and see you next week!
Page 25 of 56
ICS 224 Lab Manual
Preparation
Obtain an iPad from your instructor at the beginning of the lab
Page 26 of 56
ICS 224 Lab Manual
Now launch the app again. All additions and changes you made should have been lost, because we have not yet told iOS how
to save and load data
In the PhotoEntry, replace
class PhotoEntry: NSObject {
with
import os
class PropertyKey {
static let photo = "photo"
static let notes = "notes"
}
Page 27 of 56
ICS 224 Lab Manual
func saveObjects() {
do {
let data = try NSKeyedArchiver.archivedData(withRootObject: objects, requiringSecureCoding:
false)
try data.write(to: PhotoEntry.archiveURL)
} catch {
os_log("Cannot save due to %@", log: OSLog.default, type: .debug, error.localizedDescription)
}
}
Fix the following 3 items on your own. If you ask other students or the instructor, you will lose 5 marks! If you help
Independent
Independent
someone, you will also lose 5 marks!!
Add 1 line to fix the os_log() errors (Hint: Look at PhotoEntry)
Work
Work
Add a few lines to load objects from file and store them in the objects variable after the Master view has been loaded (Hint:
Look closely at the loadObjects() return type and the variable declarations at top of the MasterViewController class)
Add a few more lines to save objects whenever an entry is added or deleted (Hint: Look closely at all the functions in
MasterViewController)
Modify the code further so that objects are saved whenever an entry is changed (Hint:
Find the method that (A) you inserted earlier in this lab and that (B) is called whenever PhotoEntryTableViewCell Update /0
a change is made. Then set a flag there. Next, find the method in (Instructor Stamp)
MasterViewController that is the best place to check for that flag and make the code
react accordingly)
Modify the code further so the changed entry is reflected in the corresponding Load/Save IF Needed /0
PhotoEntryTableViewCell (Hint: You may have to call (Instructor Stamp)
tableView.reloadData() to make sure changes are shown in the list of entries)
When you are ready, place a breakpoint on loadObjects() and saveObjects() and show your instructor that
loading and saving is only done when required Source Code
Commit and push all your changes /20
Print out a copy of all your Swift code and attach it to this page. Note that Appendix A will be
applied, so be sure to structure your code well, check for errors, and document your work
Page 28 of 56
ICS 224 Lab Manual
3. Using ScrollViews
Depending on the rotation and the device (e.g., iPhone landscape), the keyboard can completely block out the notes section.
There are various ways to fix this. We'll use Scroll Views
Click on the main story board
Drag a Scroll View into the Detail Scene's View, just underneath the Safe Area (the left panel, not
the right panel)
Drag the Stack View in to the Scroll View, just underneath the Frame Layout Guide
Control-drag from the Scroll View to the Safe Area and select the first 4 options, one at a
time (see screenshot on the right)
The Scroll View should now take up the entire Safe Area (click on the Safe Area to see its
dimensions)
Control-drag from the Stack View to the Content Layout Guide and select the first 4 options,
one at a time (see screenshot on the right)
Select the Stack View in the left panel and click on the Add New Constraints button (see Appendix B)
Control-drag from the Stack View to the Scroll View and select Equal Widths
Click on the Stack View and click on t the Add New Constraints button (see Appendix B)
Set the Height to 1000
In DetailViewController, add the following to the class:
let OFFSET: CGFloat = 10
At the bottom of viewDidLoad() in DetailViewController, add the following code
NotificationCenter.default.addObserver(self, selector: #selector(keyboardAppeared), name:
UIWindow.keyboardDidShowNotification, object: nil)
NotificationCenter.default.addObserver(self, selector: #selector(keyboardDisappeared), name:
UIWindow.keyboardDidHideNotification, object: nil)
Now add the following methods:
@objc func keyboardAppeared(_ notification: NSNotification) {
guard let frameValue = notification.userInfo?[UIResponder.keyboardFrameBeginUserInfoKey] as?
NSValue else {
return
}
let frame = frameValue.cgRectValue
scrollVIew.contentInset.bottom = frame.size.height + OFFSET
scrollVIew.verticalScrollIndicatorInsets.bottom = frame.size.height + OFFSET
}
Page 29 of 56
ICS 224 Lab Manual
}
Run the app on the iPad as well as the iPhone (using the Simulator); check both rotations on both devices to make sure you
can now scroll to the notes section
4. Completion
Log out of your Mac
Delete all photos and your app from the iPad, then return the iPad
Congratulations! You have completed this lab. Be sure to hand in this lab, along with your printouts, and see you next week!
Page 30 of 56
ICS 224 Lab Manual
Preparation
Obtain an iPad from your instructor at the beginning of the lab
Page 31 of 56
ICS 224 Lab Manual
Page 32 of 56
ICS 224 Lab Manual
Independent
Independent
Do the following on your own. If you ask other students or the instructor, you will lose 5 Marks! If you help other
students, you will also lose 5 Marks!!
Note that photos are not currently saved when selecting another entry; fix this problem, just like you did for the notes portion
Work
Work
of the view
Also, make sure the photos are saved when the app terminates, or when it is launched again
Update the PhotoEntryTableViewCell with the new image
Right now, on an iPad, the camera icon is enabled even if there are no entries, or if no entry has been selected, or all
entries have been deleted. Correct this so that the camera icon is only enabled when an actual entry has been selected. If
you don't recall how to enable or disable buttons, review Lab 1
Also hide or remove the image and notes when all entries have been deleted
Camera Support /0
Test your app thoroughly
(Instructor Stamp)
Commit and push all changes
Demo your working app to your instructor
Page 33 of 56
ICS 224 Lab Manual
Run the app and confirm that you can add photos from the photo library. If the photo
library is empty, take a few photos to populate it, then try again to add the photos from Photo Library Support /0
the photo library to your app (Instructor Stamp)
Demonstrate to your instructor that photo library access works
Independent
Do this Section on your own. If you ask other students or the instructor, you will lose 5 Marks! If you help others, you
will also lose 5 Marks!!
Add a Date Picker from the Object Library to the bottom of the DetailViewController
Work
Work
Assuming you name the Outlet date, you can have a function called dateChanged() be invoked whenever the date is changed
by adding the following code:
date.addTarget(self, action: #selector(dateChanged(_:)), for: .valueChanged)
Also add the lines:
@objc func dateChanged(_ sender: UIDatePicker) {
// Add code here
}
Now add support for adding dates. Dates must be saved and loaded just like notes and photos are. You may want to do some
research on UIDatePicker using the built-in Quick Help in order to be able to set dates
Demonstrate to your instructor that date support works Date Picker Support /0
(Instructor Stamp)
4. Completion
Print out a copy of ALL your modified Swift code and attach it to this page. Highlight the changes you made since the
last Lab. You can use the Version Editor (see Appendix B) to help you view all changes. Note that Appendix A will be
applied, so be sure to structure your code well, check for errors, and document your work
Log out of your Mac Source Code
Delete all photos and your app from the iPad, then return the iPad /20
Congratulations! You have completed this lab. Be sure to hand in this lab and see you next week!
Page 34 of 56
ICS 224 Lab Manual
Preparation
Obtain an iPad from your instructor at the beginning of the lab
For more details, consult Creating Document-Based iOS Apps (https://swiftdevjournal.com)
Page 35 of 56
ICS 224 Lab Manual
Page 36 of 56
ICS 224 Lab Manual
document?.updateChangeCount(.done)
}
before the call to dismiss
Run the app and make sure you can create new documents, edit them, save them, and load them again.
2. Setting up Segues
Add 5 buttons underneath the file name. Use a label with a single space character
to separate the last button
Create outlets and actions for each of the Style buttons
Now create a new Swift file called CustomizeViewController and make it a
subclass of UIViewController
In the main storyboard, add a new View Controller
Click on the View Controller (not the View; best to use the sidebar to the left)
Click on the Identity Inspector
Change the Class to CustomizeViewController. The name should change to CustomizeViewController in the storyboard as well
Add a picker, a text field, and 3 buttons and arrange them as shown on the right
Add outlets for these 5 elements
Also add the line
var pickerData = [String]()
at the top of the CustomizeViewController
Embed the CustomizeViewController in a Navigation Controller
Control drag from the Customize button to the Navigation Controller
Select Show
Click on the Show segue to "Navigation Controller"
Click on the Attribute Inspector
Change the Identity to ShowController
Click on Customize View Controller
Add a Bar Button Item to the Customize View Controller
Using the Attribute Inspector, change its System Item to Done
In DocumentViewController.swift, add the following code:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
super.prepare(for: segue, sender: sender)
if segue.identifier != "ShowController" {
return
}
Page 37 of 56
ICS 224 Lab Manual
Independent Work
Independent Work
StackOverflow is fine). If you ask other students or the instructor, you will lose 5 Marks! If you help others, you will
also lose 5 Marks!!
Make it possible to change the button labels of the DocumentViewController from the CustomizeViewController. For example, if
we pick "Style 4" in CustomizeViewController and change the label to "Emphasize", the picker should be updated, and the
corresponding button label should also be updated (see below). Specifically:
Page 38 of 56
ICS 224 Lab Manual
CustomizeViewController must conform to the UIPickerViewDataSource and UIPickerViewDelegate protocols. Review the
methods that are part of the 2 protocols and implement the correct ones
CustomizeViewController must be declared as a delegate of the picker. There is a particular method that is called once the
View has been set up. That method is best suited for the delegate declaration
Every time an entry is picked from the picker, the button label in CustomizeViewController must be updated accordingly
Every time the button label is changed, the picker in CustomizeViewController must also change accordingly. This involves
Independent Work
Independent Work
Page 39 of 56
ICS 224 Lab Manual
Preparation
Obtain an iPad from your instructor at the beginning of the lab
Page 40 of 56
ICS 224 Lab Manual
3. Adding an Object
Using Safari, go to https://developer.apple.com/augmented-reality/quick-look/ and download the biplane
Drag the biplane in to the Reality Composer
Delete the default box
Place the biplane in the centre of the scene using the Transform menu
Name it biplane
Save the scene
Run the program again and confirm that the box has been replaced by the biplane
4. Adding Behaviour
In the Reality Composer, click on View > Show Behaviours
Click on +
Select Custom Behaviour
Click on the Trigger box
Select Tap
Select the object you chose earlier
Click on Done
Click on the Action Sequence box
Select USDZ Animation (this file format was developed by Apple and Pixar for AR, and is based on Pixar's USD scene
description format)
Choose the biplane
Click on the + next to Action Sequence
Select Move, Rotate, Scale To
Choose the biplane
Change to duration to 5 seconds
Pick a new destination position
Now click on the Play button. After tapping on the biplane, it should move to the indicated position and then turn on the
propellers. This is not quite what we want.
Drag the USDZ Animation onto Move, Rotate, Scale To
Click on the Play button again
Adjust the Iterations of the USDZ Animation so that the propeller keeps moving for at Moving Plane /5
least as long as the plane is moving (Instructor Stamp)
Save the scene
Run the program again and confirm that the plane is moving once it has been tapped. Show the result to your instructor
Commit and push your code
Page 41 of 56
ICS 224 Lab Manual
5. Adding Notifications
Add a View to your ARView Scene, and inside, place an ARView and a Button, as pictured on the
right side
Back in the Reality Composer, place another object into the scene using Insert > Object. You may
have to download the object first by clicking on the cloud icon to the right of the object's section title
Add another Custom Behaviour
Click on Trigger
Select Notification
Call it startNotification
For the Action Sequence, select Orbit
Select the biplane as the Selected Object and the object you inserted above as the Center
Change the duration to 5 seconds
In ViewController.swift, modify the code so that
boxAnchor becomes an instance variable
pushing the button results in a call to boxAnchor.notifications.startNotification.post()
arView is correctly linked to the ARView you added above
When the app is working correctly, call your instructor for a demo
Commit and push all changes
6. Completion
Log out of your Mac
Delete all photos and your app from the iPad, then return the iPad Orbiting Plane /5
Congratulations! You have completed this lab. Be sure to hand in this lab and see you (Instructor Stamp)
next week!
Page 42 of 56
ICS 224 Lab Manual
Preparation
Obtain an iPad from your instructor at the beginning of the lab
Page 43 of 56
ICS 224 Lab Manual
Page 44 of 56
ICS 224 Lab Manual
statusLabel.text = "Ready"
let config = ARWorldTrackingConfiguration()
config.worldAlignment = .gravity
config.providesAudioData = false
}
Also add status messages to
func session(...)
func sessionWasInterrupted(...)
func sessionInterruptionEnded(...)
Create a function called func session(_ session: ARSession, cameraDidChangeTrackingState camera: ARCamera)
Update the statusLabel with a detailed status explanation for every possible camera tracking state. You will have to explore the
documentation a bit to find all possible states
Run the app and make sure the status messages change when:
Switching to another app and then back to your app
Covering the back camera lens
5. Positioning an Asset
Add sliders and labels to your app as illustrated on the right
Create Outlets for the labels named xLabel, yLabel, and zLabel, from top to
bottom
Create Actions for the sliders named changeX, changeY, and changeZ, from
top to bottom
For each slider, click on the Attributes Inspector, and change the default Value
to 0, the Minimum to -1, and the Maximum to +1
Make sure that the correct label is updated whenever a slider is moved
Note that you can control the formatting of a floating point value by using the
command
String(format: "%.2f", x)
This will print x as a floating number with no more than two digits after the decimal point
Make sure the box moves in accordance with the slider values. You can use the following code as a basis for this:
if let box = scene?.rootNode.childNode(withName: "box", recursively: false) {
box.position = SCNVector3Make(x, y, z)
}
where scene needs to be the same variable as scene in viewDidLoad
Test your app with varying rotations
Page 45 of 56
ICS 224 Lab Manual
When the app is working correctly, call your instructor for a demo
Commit and push all changes Sliders Move Box, Update Labels /2
(Instructor Stamp)
6. Adding Physics
At the top, add 2 buttons, one titled Launch, the other titled Adjust
Make the Adjust button trigger a segue to go to a settings screen; if you don't recall how to
implement segues, review Lab 7. Don't forget to add the prepare and unwind methods in
the main view controller, as well as a Done button
Set up the settings screen just like on the right-hand side. Specifically:
Create a settings view controller class. Don't forget to update the main story board with
this information
The settings view controller class must have an instance variable var physicsBody:
SCNPhysicsBody? that is passed in from the main view controller
Create outlets for each of the values on the right
Create outlets for each of the slider
Slider values must be derived from the corresponding value in the physicsBody
Slider values must range from 0 to 1
Create actions for each of the sliders that update the corresponding values on the right
Slider values must also be applied to the physics model of the box asset
In the main view controller, add the following to viewDidLoad
physicsBody = SCNPhysicsBody(type: .dynamic, shape: nil)
physicsBody?.isAffectedByGravity = true
physicsBody?.allowsResting = true
In the launch function, apply the physics model and position the new box using the following code:
guard let frame = self.sceneView.session.currentFrame else {
return
}
let transform = SCNMatrix4(frame.camera.transform)
let position = SCNVector3(transform.m41, transform.m42, transform.m43)
Page 46 of 56
ICS 224 Lab Manual
newPhysicsBody.angularDamping = self.physicsBody!.angularDamping
newPhysicsBody.centerOfMassOffset = self.physicsBody!.centerOfMassOffset
newPhysicsBody.charge = self.physicsBody!.charge
newPhysicsBody.damping = self.physicsBody!.damping
newPhysicsBody.friction = self.physicsBody!.friction
newPhysicsBody.mass = self.physicsBody!.mass
newPhysicsBody.restitution = self.physicsBody!.restitution
newPhysicsBody.rollingFriction = self.physicsBody!.rollingFriction
Page 47 of 56
ICS 224 Lab Manual
DispatchQueue.main.async {
let planeGeometry = SCNPlane(width: CGFloat(planeAnchor.extent.x), height:
CGFloat(planeAnchor.extent.z)) // y is always 0 for both .horizontal/.vertical
planeGeometry.firstMaterial?.diffuse.contents = UIColor.init(red: 0.5, green: 0.5, blue: 0.5,
alpha: 0.5)
let planeNode = SCNNode(geometry: planeGeometry)
planeNode.position = SCNVector3Make(planeAnchor.center.x, 0, planeAnchor.center.z)
planeNode.transform = SCNMatrix4MakeRotation(-Float.pi / 2.0, 1, 0, 0) // SCNPlane is not
oriented as we would expect; and only visible from one side!
planeNode.physicsBody = SCNPhysicsBody(type: .kinematic, shape: SCNPhysicsShape(geometry:
planeGeometry, options: nil))
planeNode.physicsBody?.restitution = 0.5
planeNode.physicsBody?.friction = 0.5
node.addChildNode(planeNode)
}
}
Page 48 of 56
ICS 224 Lab Manual
func renderer(_ renderer: SCNSceneRenderer, didUpdate node: SCNNode, for anchor: ARAnchor) {
guard let planeAnchor = anchor as? ARPlaneAnchor, node.childNodes.count > 0, let planeGeometry =
node.childNodes[0].geometry as? SCNPlane else {
return
}
DispatchQueue.main.async {
planeGeometry.width = CGFloat(planeAnchor.extent.x)
planeGeometry.height = CGFloat(planeAnchor.extent.z)
node.childNodes[0].position = SCNVector3Make(planeAnchor.center.x, 0, planeAnchor.center.z)
}
}
Download the program to the iPad
Stop the program, then untether the iPad
Run the program again
Slowly move the iPad. It should detect table tops and floors. Note that the detection is not very accurate; but keep in mind that
the CPU in your brain is a lot more capable than the one in the iPad!
Observe what happens when you drop boxes onto the surfaces or surface edges Boxes Can Be Placed On Desk /4
Show that you can place a virtual box on your desk to your instructor. You may have to (Instructor Stamp)
adjust Damping and other characteristics of the box to get this to work
8. Completion
Log out of your Mac
Delete all photos and your app from the iPad, then return the iPad
Congratulations! You have completed this lab. Be sure to hand in this lab and see you next week!
Page 49 of 56
ICS 224 Lab Manual
Preparation
Independent Work
Independent Work
Page 50 of 56
ICS 224 Lab Manual
***** - passes all tests - well-documented, allowing another programmer to use all - well-engineered, consisting of a modular collection of simple,
perfect functions based on the header comments alone single-purpose functions
- code review reveals no faults - responsibilities of all functions are described well, without - constants are used whenever appropriate
giving implementation details
- efficient (given the requirements) - all parameters, return values, and side effects are explained - globals are not used, unless unavoidable
- no redundant operations - comments within all functions are helpful, without being - all constants and variables are named appropriately
distracting, making it easy to follow along
**** - passes nearly all tests - occasionally, there are comments that are not complete, - largely well-engineered, except for a few, minor issues
good helpful, and/or true
- a code review reveals nearly no faults; faults that are found, - could be improved by slightly reworded, slightly more, or - a few, minor issues with constants, variables, or layout
are minor slightly fewer comments
- generally efficient, except in a few minor cases - easily used and reused, except in a few, minor instances
*** - passes half the tests, or more, but the failure rate is too high - in a number of cases, comments are cryptic, false, incomplete, - in need of reengineering due to a number of issues, none, or
ok for a 4-star rating misleading, missing, or redundant almost none of which, are major
- a code review reveals a number of faults, but none, or almost - on a number of occasions, there are issues with constants,
none of them, are major variables, or layout
- somewhat efficient, but there are a small number of major - often easily used and reused, but there are a small number of
inefficiencies major problems, none of which render the work unusable
Page 51 of 56
ICS 224 Lab Manual
** - fails more than half the tests - only little relevant documentation - a number of major issues, requiring major changes
fail
- a code review reveals a high number of faults, including a - comments are often cryptic, false, incomplete, misleading, - not easily used and reused
number of major faults missing, or redundant
* - fails nearly all the tests - essentially no legitimate documentation - only a few functions, many of which are responsible for too
fail many things
- code review reveals a proliferation of major faults - essentially not usable or reusable
0 - fails all tests and/or does not run - no legitimate documentation and/or does not run - no legitimate code and/or does not run
fail
Page 52 of 56
ICS 224 Lab Manual
Active Scheme Top Panel (Left) Node Inspector Right Sidebar (Scene Only)
Add New Constraints Storyboard Bottom Panel (Right) Play Top Panel (Left)
Assistant Editor Top Panel (Right) in Mojave, Quick Help Inspector Right Sidebar
Right Sidebar in Catalina
Size Inspector Right Sidebar
Attributes Inspector Right Sidebar
Source Control Navigator Left Sidebar
Breakpoint Navigator Left Sidebar
Standard Editor Top Panel (Right)
Continue Program Execution Debug Area Top Panel (Left)
Step Over Debug Area Top Panel (Left)
Debug Navigator Left Sidebar
Stop Top Panel (Left)
Embed Storyboard Bottom Panel (Right)
Test Navigator Left Sidebar
Exit Segue Segues (Above View Controllers
in Storyboard) Version Editor Top Panel (Right)
Find Navigator Left Sidebar
Page 53 of 56
Project
Navigator Library Play
Source Control
Navigator
Standard
Left Sidebar
Editor Stop
.
Top Panel (Left)
Assistant
Library
macOS Mojave (left) and macOS Catalina (right) appear slightly different
Version Editor
Page 54 of 56
In Mojave, the Library button is only visible if a story board has been selected
ICS 224 Lab Manual
.
ICS 224 Lab Manual
Right Sidebar
.
Quick Help
Inspector
Identity
Inspector
Attributes
Inspector
Size Inspector
Editor Options
(incl. Assistant)
Quick Help
Inspector
Identity
Inspector
Attributes
Inspector
Size Inspector
.
macOS Mojave (left) and macOS Catalina (right) appear slightly different
In macOS Catalina, the Editor Options button is only visible if the storyboard is selected; it will then provide an option to set the
Assistant view
Quick Help
Inspector
Node Inspector
Attributes
Inspector
Embed
Align
Add New
Constraints
Align
Add New
Constraints
Embed
macOS Mojave (left) and macOS Catalina (right) appear slightly different
Page 55 of 56
ICS 224 Lab Manual
Continue Program
Execution
Step Over
.
Segues (Above View Controllers in Storyboard)
.
Exit Segue
Page 56 of 56