<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://homeostasis.scs.carleton.ca/wiki/index.php?action=history&amp;feed=atom&amp;title=Mobile_App_Development_2022W_Lecture_8</id>
	<title>Mobile App Development 2022W Lecture 8 - Revision history</title>
	<link rel="self" type="application/atom+xml" href="https://homeostasis.scs.carleton.ca/wiki/index.php?action=history&amp;feed=atom&amp;title=Mobile_App_Development_2022W_Lecture_8"/>
	<link rel="alternate" type="text/html" href="https://homeostasis.scs.carleton.ca/wiki/index.php?title=Mobile_App_Development_2022W_Lecture_8&amp;action=history"/>
	<updated>2026-04-06T01:52:59Z</updated>
	<subtitle>Revision history for this page on the wiki</subtitle>
	<generator>MediaWiki 1.42.1</generator>
	<entry>
		<id>https://homeostasis.scs.carleton.ca/wiki/index.php?title=Mobile_App_Development_2022W_Lecture_8&amp;diff=23786&amp;oldid=prev</id>
		<title>Soma at 18:38, 4 February 2022</title>
		<link rel="alternate" type="text/html" href="https://homeostasis.scs.carleton.ca/wiki/index.php?title=Mobile_App_Development_2022W_Lecture_8&amp;diff=23786&amp;oldid=prev"/>
		<updated>2022-02-04T18:38:30Z</updated>

		<summary type="html">&lt;p&gt;&lt;/p&gt;
&lt;table style=&quot;background-color: #fff; color: #202122;&quot; data-mw=&quot;interface&quot;&gt;
				&lt;col class=&quot;diff-marker&quot; /&gt;
				&lt;col class=&quot;diff-content&quot; /&gt;
				&lt;col class=&quot;diff-marker&quot; /&gt;
				&lt;col class=&quot;diff-content&quot; /&gt;
				&lt;tr class=&quot;diff-title&quot; lang=&quot;en&quot;&gt;
				&lt;td colspan=&quot;2&quot; style=&quot;background-color: #fff; color: #202122; text-align: center;&quot;&gt;← Older revision&lt;/td&gt;
				&lt;td colspan=&quot;2&quot; style=&quot;background-color: #fff; color: #202122; text-align: center;&quot;&gt;Revision as of 18:38, 4 February 2022&lt;/td&gt;
				&lt;/tr&gt;&lt;tr&gt;&lt;td colspan=&quot;2&quot; class=&quot;diff-lineno&quot; id=&quot;mw-diff-left-l5&quot;&gt;Line 5:&lt;/td&gt;
&lt;td colspan=&quot;2&quot; class=&quot;diff-lineno&quot;&gt;Line 5:&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td class=&quot;diff-marker&quot;&gt;&lt;/td&gt;&lt;td style=&quot;background-color: #f8f9fa; color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #eaecf0; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;div&gt;* [https://homeostasis.scs.carleton.ca/~soma/mad-2022w/lectures/comp1601-2022w-lec08-20220204.cc.vtt auto-generated captions]&lt;/div&gt;&lt;/td&gt;&lt;td class=&quot;diff-marker&quot;&gt;&lt;/td&gt;&lt;td style=&quot;background-color: #f8f9fa; color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #eaecf0; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;div&gt;* [https://homeostasis.scs.carleton.ca/~soma/mad-2022w/lectures/comp1601-2022w-lec08-20220204.cc.vtt auto-generated captions]&lt;/div&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td class=&quot;diff-marker&quot;&gt;&lt;/td&gt;&lt;td style=&quot;background-color: #f8f9fa; color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #eaecf0; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;div&gt;Video is also available through Brightspace (Resources-&amp;gt;Zoom Meetings (Recordings, etc.)-&amp;gt;Cloud Recordings tab).  Note that here you&amp;#039;ll also see chat messages.&lt;/div&gt;&lt;/td&gt;&lt;td class=&quot;diff-marker&quot;&gt;&lt;/td&gt;&lt;td style=&quot;background-color: #f8f9fa; color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #eaecf0; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;div&gt;Video is also available through Brightspace (Resources-&amp;gt;Zoom Meetings (Recordings, etc.)-&amp;gt;Cloud Recordings tab).  Note that here you&amp;#039;ll also see chat messages.&lt;/div&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td class=&quot;diff-marker&quot; data-marker=&quot;−&quot;&gt;&lt;/td&gt;&lt;td style=&quot;color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #ffe49c; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;div&gt;&lt;del style=&quot;font-weight: bold; text-decoration: none;&quot;&gt;&lt;/del&gt;&lt;/div&gt;&lt;/td&gt;&lt;td colspan=&quot;2&quot; class=&quot;diff-side-added&quot;&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td class=&quot;diff-marker&quot; data-marker=&quot;−&quot;&gt;&lt;/td&gt;&lt;td style=&quot;color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #ffe49c; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;div&gt;&lt;del style=&quot;font-weight: bold; text-decoration: none;&quot;&gt;(Files are being uploaded now)&lt;/del&gt;&lt;/div&gt;&lt;/td&gt;&lt;td colspan=&quot;2&quot; class=&quot;diff-side-added&quot;&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td class=&quot;diff-marker&quot;&gt;&lt;/td&gt;&lt;td style=&quot;background-color: #f8f9fa; color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #eaecf0; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;br&gt;&lt;/td&gt;&lt;td class=&quot;diff-marker&quot;&gt;&lt;/td&gt;&lt;td style=&quot;background-color: #f8f9fa; color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #eaecf0; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;br&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td class=&quot;diff-marker&quot;&gt;&lt;/td&gt;&lt;td style=&quot;background-color: #f8f9fa; color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #eaecf0; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;div&gt;==Notes==&lt;/div&gt;&lt;/td&gt;&lt;td class=&quot;diff-marker&quot;&gt;&lt;/td&gt;&lt;td style=&quot;background-color: #f8f9fa; color: #202122; font-size: 88%; border-style: solid; border-width: 1px 1px 1px 4px; border-radius: 0.33em; border-color: #eaecf0; vertical-align: top; white-space: pre-wrap;&quot;&gt;&lt;div&gt;==Notes==&lt;/div&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;/table&gt;</summary>
		<author><name>Soma</name></author>
	</entry>
	<entry>
		<id>https://homeostasis.scs.carleton.ca/wiki/index.php?title=Mobile_App_Development_2022W_Lecture_8&amp;diff=23785&amp;oldid=prev</id>
		<title>Soma: Created page with &quot;==Video==  Video from the lecture given on February 4, 2022 is now available: * [https://homeostasis.scs.carleton.ca/~soma/mad-2022w/lectures/comp1601-2022w-lec08-20220204.m4v...&quot;</title>
		<link rel="alternate" type="text/html" href="https://homeostasis.scs.carleton.ca/wiki/index.php?title=Mobile_App_Development_2022W_Lecture_8&amp;diff=23785&amp;oldid=prev"/>
		<updated>2022-02-04T18:34:41Z</updated>

		<summary type="html">&lt;p&gt;Created page with &amp;quot;==Video==  Video from the lecture given on February 4, 2022 is now available: * [https://homeostasis.scs.carleton.ca/~soma/mad-2022w/lectures/comp1601-2022w-lec08-20220204.m4v...&amp;quot;&lt;/p&gt;
&lt;p&gt;&lt;b&gt;New page&lt;/b&gt;&lt;/p&gt;&lt;div&gt;==Video==&lt;br /&gt;
&lt;br /&gt;
Video from the lecture given on February 4, 2022 is now available:&lt;br /&gt;
* [https://homeostasis.scs.carleton.ca/~soma/mad-2022w/lectures/comp1601-2022w-lec08-20220204.m4v video]&lt;br /&gt;
* [https://homeostasis.scs.carleton.ca/~soma/mad-2022w/lectures/comp1601-2022w-lec08-20220204.cc.vtt auto-generated captions]&lt;br /&gt;
Video is also available through Brightspace (Resources-&amp;gt;Zoom Meetings (Recordings, etc.)-&amp;gt;Cloud Recordings tab).  Note that here you&amp;#039;ll also see chat messages.&lt;br /&gt;
&lt;br /&gt;
(Files are being uploaded now)&lt;br /&gt;
&lt;br /&gt;
==Notes==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Lecture 8&lt;br /&gt;
---------&lt;br /&gt;
&lt;br /&gt;
In SwiftUI, you *really* don&amp;#039;t want to do explicit typing because the types under the hood get crazy complicated&lt;br /&gt;
  - I did some forced conversions and got a runtime error with a type that was several lines long&lt;br /&gt;
  - use implicit typing wherever you can, everything works better&lt;br /&gt;
&lt;br /&gt;
In lines 62-64 of remotePicViewer, there&amp;#039;s a ternary operator checking the &amp;quot;moved&amp;quot; boolean variable&lt;br /&gt;
                    .position(moved ? position :&lt;br /&gt;
                                CGPoint(x: g.size.width / 2,&lt;br /&gt;
				        y: g.size.height / 2))&lt;br /&gt;
&lt;br /&gt;
What this is saying is that if moved is true, return position, otherwise return&lt;br /&gt;
the CGPoint&lt;br /&gt;
&lt;br /&gt;
When will moved be true?&lt;br /&gt;
 - once the user has dragged the image&lt;br /&gt;
&lt;br /&gt;
When will it be false?&lt;br /&gt;
 - when the app starts up and when a new image has been selected&lt;br /&gt;
&lt;br /&gt;
Question: why not just initialize position to be the fixed CGPoint value&lt;br /&gt;
  (that is in the center of the GeometryView box)?&lt;br /&gt;
&lt;br /&gt;
Why not just&lt;br /&gt;
 - set position to the centered point when position is initialized?&lt;br /&gt;
 - and reset position when we change to a new image?&lt;br /&gt;
     - well, g is out of scope&lt;br /&gt;
&lt;br /&gt;
What about at the top of GeometryReader?&lt;br /&gt;
  - But we can&amp;#039;t, we get an error &amp;quot;Type &amp;#039;()&amp;#039; cannot conform to &amp;#039;View&amp;#039;&amp;quot;&lt;br /&gt;
&lt;br /&gt;
What this error means is we&amp;#039;re trying to do normal Swift things where we should be doing SwiftUI things&lt;br /&gt;
 - i.e., everything inside a View has to be a View&lt;br /&gt;
&lt;br /&gt;
The body of a View is not a normal function&lt;br /&gt;
 - you can&amp;#039;t set arbitrary variables, put in loops, etc&lt;br /&gt;
 - everything needs to generate a View&lt;br /&gt;
&lt;br /&gt;
The body of a View is written in a domain-specific language, SwiftUI&lt;br /&gt;
&lt;br /&gt;
But that isn&amp;#039;t the real reason&lt;br /&gt;
&lt;br /&gt;
The real reason is, how often is the body of a view being evaluated?&lt;br /&gt;
 - potentially VERY frequently&lt;br /&gt;
 - every time the screen is updated (and with animation that can be very often)&lt;br /&gt;
&lt;br /&gt;
To make View updates efficient (and more importantly, optimizable), the state of a View can&amp;#039;t change while it is being calculated&lt;br /&gt;
 - so you *can&amp;#039;t* change @State variables in the body of a View, because&lt;br /&gt;
   that would change the View&amp;#039;s state, and so would change how it should be rendered&lt;br /&gt;
&lt;br /&gt;
So if you see the error &amp;quot;Type &amp;#039;()&amp;#039; cannot conform to &amp;#039;View&amp;#039;&amp;quot;, you probably tried to modify a @State variable inside the body of a View.&lt;br /&gt;
 - you have to do it in closures/functions that will be evaluated later&lt;br /&gt;
&lt;br /&gt;
When you declare a function, you are really saying &amp;quot;here is code that should be run at a later time&amp;quot;&lt;br /&gt;
 - so declaring a function inside of a view makes sure it won&amp;#039;t be run&lt;br /&gt;
   while the view is being updated&lt;br /&gt;
&lt;br /&gt;
To setup gestures, we call the .gesture method of the view and pass it &amp;quot;some Gesture&amp;quot; (i.e., some struct that will follow the Gesture protocol)&lt;br /&gt;
&lt;br /&gt;
Normally you won&amp;#039;t define these manually, you&amp;#039;ll instead use pre-defined ones for standard gestures&lt;br /&gt;
  - MagnificationGesture&lt;br /&gt;
  - DragGesture&lt;br /&gt;
  - RotationGesture&lt;br /&gt;
  - TapGesture&lt;br /&gt;
You can also combine these with SimultaneousGesture&lt;br /&gt;
&lt;br /&gt;
There are also faster ways of declaring these with things like &amp;quot;onTapGesture&amp;quot;&lt;br /&gt;
  - then we just have to give the actions rather than create a whole Gesture struct&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
For gestures, we declare functions that are called at various states during and after the gesture, such as&lt;br /&gt;
 - onChanged &amp;lt;-- as the gestures is changing, this is called (potentially many times)&lt;br /&gt;
 - onEnded &amp;lt;-- called once the gesture is ended&lt;br /&gt;
&lt;br /&gt;
For things like .onTapGesture, which doesn&amp;#039;t really have a &amp;quot;during&amp;quot; phase, we just have a &amp;quot;perform&amp;quot; function that is called when the action happens&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Soma</name></author>
	</entry>
</feed>