ストリーミングはほとんどのブラウザと
Developerアプリで視聴できます。
-
ClassKitに関する新機能
ClassKitフレームワークは、Schoolworkアプリケーションを通して、App内での教育活動を教師に示す上で役立ちます。メタデータのプロパティと進捗報告を強化することで、学生と教師に豊かなアサインメント経験を提供する方法を紹介します。また、新しいClassKit Catalog APIによって、コンテンツの管理とAppの管理が切り離され、全体的な検出可能性がどのように改善されるのかを説明します。
リソース
関連ビデオ
WWDC20
-
ダウンロード
こんにちは WWDCへようこそ “ClassKitに関する新機能” バスカランと申します Apple Educationチームのエンジニアです 本日は私の同僚であるダニエルと共に ClassKitの最新の変更内容についてお話し 皆様の知識をアップデートしたいと考えています 最初にClassKitのどの機能が 強化されたかについて説明します これらの機能強化によってあなたの アプリケーションのコンテンツを 今まで以上に細かに操作できるようになりました
続いてClassKitの適用にあたってお薦めできる ベストプラクティスをいくつか説明します その後ダニエルがコンテンツを レポートする新しい方法を紹介します ここではClassKit Catalog APIと呼ばれる サービスを使用します 最後に同じくダニエルが ClassKit Catalog APIを適用するための ベストプラクティスのいくつかを説明します それではClassKitの全般的な事項の 簡単な説明から始めましょう ClassKitはAppleエデュケーション· エコシステムの中核となるコンポーネントです
ClassKitはアプリケーションの教育コンテンツを アクティビティとして表面に 浮き上がらせるフレームワークで 先生たちはこれらのアクティビティを 生徒に課題として割り振ることができます さらにClassKitを使用すれば 生徒が自分の課題をどの程度こなしたか アプリケーションを使用して 報告できるようになります ここで最も重要なポイントはその生徒の プライバシーが厳格に保護されることです つまり報告されるのは課題アクティビティの 進捗状況に限定されます たとえば教師が生徒に Fun with Scienceというブックの 1つの章を読む課題を与えたところ 一人の生徒がBasic Arithmeticの 1つの章も読んだとします この場合課題として与えられたのは Fun with Scienceを読むことでしたから 先生と生徒がチェックするのは こちらの進捗状況だけです ClassKitが導入されたのは2018年のことでした 現在ではmacOSでも利用できるようになり ネイティブアプリケーションや Catalystアプリケーションの作成で使用されます
ClassKitの更に詳しい情報については 2019年の私たちのセッション “What's New in ClassKit”と 2018年のセッション “Introducing ClassKit”をご覧ください
ClassKitの何が強化されたのかを見る前に あなたのアプリケーションのコンテンツの Schoolworkのアクティビティでの表示を 簡単に調べてみましょう あなたのアプリケーションは ClassKitを使用してコンテンツを定義して それをアクティビティとして記述します ClassKitはSchoolworkを使用して ブラウズすることができます Schoolworkを使用すればクラス教材の共有や アプリケーション内で特定のアクティビティを 生徒に割り付ける 生徒との協同作業生徒進捗状況を表示するなどの 作業を簡単に実行することができます Schoolworkを開くと まずこの画面が表示されます この画面は先生が生徒に割り付けるすべての コンテンツのホームベースとして機能します
新しいハンドアウトを作成するには右側の 上端にあるNew Handoutボタンをタップします ズームインして見やすくしましょう App Activitiesをタップしてアプリケーション アクティビティ選択機能を表示します
これにより アプリケーションアクティビティ選択機能が ClassKit対応アプリケーション一覧を表示します ここではアクティビティを含む 3種類のアプリケーションが表示されています このプレゼンでは例として Book Readerアプリケーションを使用します それではBook Readerの内部にある アクティビティを見ていきましょう Fun with Scienceという名前のブックが表示され このブックはアクティビティを含んでいます Fun with Scienceにどのようなアクティビティが 含まれているのか閲覧してみましょう Fun with Scienceは何種類かの アクティビティを含み これらのアクティビティは 章として分類されています “Inquiry”というタイトルの付いた第1章の 中身を見てみましょう
この章には1つのアクティビティがあり その名前はScience Investigationです このアクティビティについて調べてみましょう Science Investigationのセクションの 最後にクイズが用意されています ところでアクティビティの内容が事細かに 表示されていることに気付かれたでしょうか?
ここにサムネイルがあって アクティビティの要約事項が書かれています 具体的には想定されている 対象年齢や完了までの時間 アプリケーションが報告するアクティビティの 進捗のタイプなどです これらの詳細情報をもとにして このアクティビティを課題の中で使用するか どうかを教師が判断します 次にこれらの 詳細事項を私たちのアプリケーションの アクティビティへ追加する方法を説明します この作業の前に App Activitiesについて簡単に調べてみます
アプリケーションのアクティビティとはあなたの アプリケーションに割り付けた任意のコンテンツです ブックの章もアクティビティですし ポッドキャストのメディアストリーム テストクイズなどもアクティビティです
アクティビティはあなたアプリケーションにより 定義され階層的に構造化されます
私たちの例を見てみましょう ここに示すのがFun with Scienceという タイトルのブックのアクティビティ階層構造です
この階層の一番上にあるのがブック Fun with Scienceです その子供階層にあたるのが ブックのそれぞれの章になります それぞれの章に含まれるセクションは 孫階層となり階層化はさらに進みます アクティビティをSchoolworkに表面を整えるには どうするのだろうかとお考えかも知れません その目的のためには ClassKitのCLSContextクラスを使用して CLSContextのインスタンスを作成し それぞれのアクティビティを表現します ClassKitはあなたのアプリケーションのために Main App Contextと呼ばれる ルートコンテキストを提供します これがあなたのアクティビティ階層構造の 親になります Main App Contextがこれですね
次に最上階のアクティビティである Fun with ScienceのCLSContextを作成して それをMain App Contextに子供として追加します
アクティビティの階層構造を一段下側へ移動して
各アクティビティに対応するコンテキストを 作成しそれを親コンテキストに追加します さてここで私は1つの例として 進度判定クイズを積極的に利用して そのアクティビティに詳細事項を 追加する方法を説明しようと思います 少し前に見たように 何項目から詳細事項が存在します 以下順次ステップを追って これらの詳細事項をクイズコンテキストに 追加する方法を見ていただきます まず最初に サムネイルとサマリーをクイズコンテキストに 追加する方法について説明します まずそのアクティビティに対応する コンテキストを作成します このケースでは 進度判定クイズがこれに該当します 次にサマリーをコンテキストに追加します 何についてのクイズなのかを説明する訳です そしてサムネイルを追加します ClassKitではサムネネイルのサイズが 330x330ピクセルに制限されることを忘れずに 必要ならば小型化することも可能せす この例では 画像アセットmeasurements_quiz.jpgを利用して サムネイルを作成します ここでファイルURLから サムネイルを取得するために thumbnailFromImage関数を使用していることに 注意してください この関数について調べてみましょう
関数はファイルURLからメモリ効率の良い方法で サムネイルを作成する方法を示してくれます この過程でCoreGraphicsを使用します まずファイルから画像ソースを作成します....
次にサムネイル作成で使用する 何種類かのオプションを設定します 常に画像からサムネイルを作成するものとして その最大サイズを330ピクセルとします
次にサムネイルを作成して返します これがサムネイルを作成する1つの方法です もしあなたにとって UIImageの方が手に入り易いのであれば そのCGImageプロパティを取得して それをサムネイルとして使用することも可能です ただしこの方法を用いると あなたのアプリケーションが使用するメモリ量が 大幅に増加しますので注意が必要です オーケー さらに何項目かのプロパティを クイズコンテキストに追加しましょう 対象年齢と予測完了時間を追加します これらのプロパティの追加は非常に簡単です 値はいずれも範囲として指定します 対象年齢は9才から11才と設定して 予測完了時間は15分から20分の範囲とします 次にクイズアクティビティに関連して 報告される進捗データーのタイプを追加します この例では4種類の 進捗データが報告されています 進捗度を表すパーセント値 それぞれの質問への正/誤回答スコア
クイズへ回答するために 生徒が利用したヒントの数 および全体スコアです これらのいくつかをクイズコンテキストに 追加する方法を説明します 最初に進捗度をパーセント値として 報告する機能を作成します
この機能をサポートする CLSProgressReportingCapabilityクラスは “kind”と“details”という 2つのプロパティを持っています
“kind”を“percent kind”へ設定し “details”を “descriptive text”へ設定します 次にクイズを解くときに使用された ヒントの数を報告する機能を作成します ご覧のように それぞれの報告機能の作成は非常に簡単です 最後にこれらの機能を クイズコンテキストへ追加します この例では私は 機能の詳細を英語で設定しましたが これらはユーザーから見える文字列ですから 現在のロケールに基づいて 実行時にローカライズしてください この操作はユーザーから見える アクティビティタイトルを設定するときに 使用した方法によく似ています オーケー ここまででアプリケーションのアクティビティに 新しいプロパティを追加する方法が分かりました こうしてあなたのアプリケーションの アクティビティを豊かにしてゆけます それではあなたのアプリケーション用 コンテキストの作成と管理に役立つ お勧めベストプラクティスをいくつか紹介します
CLSContextの新らしいプロパティによって 教師にとって貴重なメタデータが追加されました 教師はこれらのメタデータを介して アプリケーションが持つ豊富な アクティビティセットの情報を知れます
ですからコンテキストを作成するときは できるだけ多くのメタデータを盛り込んだ 完備したコンテキストを作るようにしてください
コンテキストがアプリケーションの旧バージョン によって保存されていることが分かったならば 欠落しているプロパティを追加更新してください
逆にアプリケーションが古いプロパティを もはや必要としなくなったときは それらのプロパティを削除してください 削除することによりあなたのアプリケーションが サポートするアクティビティリストで非表示になり
アプリケーションがコンテキストプロバイダが 提供する拡張機能を使用して コンテキストを作成しているなら アプリケーションの拡張機能も 同様に更新してください
私の話はこれでほぼ終了です デニスが新しくなったClassKit Catalog APIに ついて話したいようです でも最後に我々がCLSContextに追加した何点かの 機能強化についてお話しさせてください これらはお客様から リクエストの多かった機能であり
identifierPathの読み出し専用プロパティが その例です このプロパティはコンテキストの 完全なidentifierPathを返します さらに新規コンテキストタイプ“course”と 1つの新規コンテキストタイプ“custom”を返す 予め定義されているタイプのどれをとっても アプリケーションのコンテンツに合わない場合 このプロパティを使用してください 設定可能なオプションプロパティを使用すれば あなたのカスタムコンテキストに命名でき 任意のコンテキストが割り付け禁止アクティビティ だと示すマーキングとしてこれを利用できます このプロパティがどのような場面で 特に役立つのか見てみましょう 私たちの例ではブックに対応する コンテキストを作成しました Fun with Scienceというブック全体が 割り当て可能なアクティビティであることを このプラスシンボルが示しています しかし教師がブック全体を 割り当てることはないと思います 実際のところデベロッパーの観点からも ブックを割り当て可能なアクティビティに しようとは考えませんでした ブックに対応するCLSContextを章をまとめる コンテナーとして使っただけのことです
ここでコンテキストの新しいisAssignable プロパティの値を“false”に設定すると ブックが割り当て可能な アクティビティではないことが明確になります ClassKitに対して 実施した機能強化の全体を理解して頂くため 更新後のデベロッパードキュメントを 是非ご覧になるようお勧めします 今説明した内容は ClassKitへの最新の機能強化項目なのです
ここまで説明したところでダニエルに来てもらい とてもワクワクする 新しいClassKit Catalog APIを 紹介してもらいましょう さあダニエル先へ進めてください どうも有難うダスカラン 本日は新しいWebサービスである ClassKit Catalog APIを 紹介したいと思います このサービスを開発する動機付けとなったのは ClassKit対応アプリケーションを構築される デベロッパーの皆様と使用する教師の皆様に 更に素晴らしいエクスペリエンスを 提供したいという思いでした 特に有用と思われるいくつかの考えを抱いて 開発にあたりました まず最初に Schoolwork内部で見つけ出すのを 容易にしたいというのが我々の希望でした 皆様のアプリケーションのユーザーから見て 提供した豊富なコンテンツリポジトリが 容易に見て取れるようでなければなりません 毎回それぞれのピースをチェックする作業が 必要であってはいけないのです
次により広い範囲の ClassKit対応コンテンツへのサポートを 他の方法に頼るのではなく CLSContextを作成するというネイティブな アプローチを使用して 提供できるようにしたかったのです
最後にコンテンツの管理と アプリケーションの管理 という2つの問題を切り離したかったのです コンテンツの変更は常に起こり得るのですが アプリケーションそのものを変更することなく コンテンツの修正が可能であるべきなのです どのようにしてこれを実現できるでしょうか? 現在CLSContextsはあなたのアプリケーションで ネイティブに定義されています 教師がアプリケーションを使用するとき アプリケーションは必要なコンテキストの生成を ClassKitに任せます そしてこれらのコンテキストが 教師のデバイスに保存され それに続いて 生徒のデバイスに保存されることになります
ClassKit Catalog APIはあなたのコンテンツを 報告する別な方法を処方してくれます
この新しいサービスを使用するためには まず既存のCLSContext階層構造を JSON構造へと翻訳するところから始めます 次にペイロードを取込み ClassKit Catalog APIを使用して それをアップロードします
そこからはあなたの提供するデータを使用して 教師または生徒のデバイス上に LSContextを作り上げる作業を行います あなたのアプリケーションが Schoolworkで参照されているときは 常にこの作業が必要となります 次に進む前に ClassKit Catalog APIとはSchoolworkで 誰でも見ることのできるコンテンツを対象とした APIであることを意識することが重要です たとえば動的に生成されるコンテンツや ユーザーに固有なCLSContextsなどの プライベートコンテンツは これからもネイティブAPIを使用してClassKit へ 報告されなければなりません あなたがリクエストするための 新しいアドレスが用意されています api.classkit-catalog.apple.com.
APIのバージョンを示す “v1” というサフィックスが付いています 将来変更が生じた場合は このサフィックスが変化してます
API自体は2つの主要コンポーネントから 構成されています 一方はコンテキストを管理し 他方はサムネイルを管理します
コンテキストはあなたのコンテンツを 説明すると同時に カタログが作用する対象となる基本ユニットです
これらの基本ユニットは バスカランが前に説明した CLSContextsであると考えてかまいませんが いくつかの付加機能が付いていますので 注意が必要です これらの付加機能については もう少し先へ進んでから詳しく説明します
サムネイルとはあなたのコンテキストに 関連付ける画像です 今回のプレゼンの最初の部分で ClassKitを使用して ネイティブに関連付ける方法を見てきました APIを使用する場合は サムネイルのエンドポイントを使用しますが これについても後ほど詳しく説明します 本日のプレゼンでは POSTリクエストに焦点を合わせて説明します コンテキストに関する POSTリクエストから見ましょう
POSTリクエストはこの例に示すように 必須フィールドを含みますから 何かを記入しなければなりません 最初のフィールドは“environment” というラベルの付いたクエリパラメータです このフィールドはあなたが実施する変更が 開発環境を対象とするのか あるいは製造向けなのかを決定します
これを利用するのかについては もう少し後で説明します 次に数項目のヘッダーに記入します ここではContent-TypeとAuthorizationです
Content-Typeにはこれから 配送するペイロードのタイプを記入します このエンドポイントでは application/jsonとする必要があります
Authorizationにはあなたが我々のサービスから 認証を受けるためのクレデンシャルを記入します
ClassKit Catalog APIのために 我々はJSON Web Tokenを採用しました これは認証に使用されている 産業標準アプローチの1つであり Appleのいくつかのウェブサービスにまたがって 使用されています
これらのトークンを生成する方法については 後ほど詳しく説明します
このリクエストの本体部分には これから作成や更新するコンテキストのリストが JSON形式で記述されなければなりません これらのコンテキストはあなたの アプリケーションのCLSContextsを表すとともに あなたのアプリケーションの機能が適正に 表現されるためには あなたのClassKit対応アプリケーションに 関連付けられたコンテキストツリーの全体が 報告されなければなりません
1つのコンテキストはデータとメタデータの 2つのフィールドから構成されています 2つのフィールドがどのように作られているのか もう少し詳しく見てみましょう データオブジェクトはCLSContextから直接 取り出した複数のフィールドから構成されており ClassKitの最新アップデートで追加された 新規フィールドもこの中に含まれます これについてはバスカランが 前に説明したとおりです
このデータオブジェクトを作成するときは あなたのアプリケーションがすでに 作成済みのCLSContextに含まれるフィールドの 値を使用します アプリケーションが作成したときの本体の コンテキストにマッチしていることを確認ください その理由はあなたのコンテンツがカタログ内で 適正に表現される必要があるからです
メタデータフィールドは CLSContextでは表現されていない 情報のキャプチャを目的としています メタデータには3つのフィールドがあります “locale”はあなたのコンテンツを異なる言語間 アプリケーションを使用する地域間で区別します “minimumBundleVersion”はクライアントの ためのヒットとして機能して このコンテキストがあなたのアプリケーションの バージョンによってサポートされているかを決定 そして”keywords”はあなたのコンテンツを 正確に説明していると考える 複数のタグを表しています メタデータはスパースオブジェクトですが APIとともに成長してゆくものと期待しています
これがコンテキストに対応する POSTリクエストの例でした
このエンドポイントについての詳細は コンテンツに対応する GETとDELETEメソッドとともに Apple Developerドキュメントとして 公開される予定です
現時点では コンテキストエンドポイントについての 何項目かのガイドラインを 強調するだけにしておきます 第一に1つのPOSTリクエストあたり200 コンテキストまでという上限が設定されています これを超える場合は複数のリクエストに 分割しなければなりません
複数に分割した場合は 子コンテキストを親の後で提出するという 順番を守る必要があります メインアプリケーションのコンテキストは 別として親が存在しない 子コンテキストは無効と判断されます 最後にあるコンテキストを 削除すると決定したとすると もしそのコンテキストに子孫が存在すれば それらの子孫も同時に削除されます アプリケーションのコンテキスト階層構造の 整合性を担保するために必要な措置です 次へ移りましょう サムネイルをアップロードする POSTメソッドについて調べてみます
ここに示すのがその例でありリクエストが 備えるべきフィールドを持っています
ます最初はサムネイルへの参照から始まります この参照を使用してサムネイルを 1つ以上のコンテキストと関連付けます
この関連付けはコンテキスト オブジェクト上のサムネイルフィールドと 対照させることによって行われます
このリクエストの残りの部分は 私たちが見た最初の部分とよく似ています たとえばクエリパラメータ “environment”を使用して 対象とする環境を指定しなければなりません
Authorizationヘッダーを使用して クレデンシャルを与え Content-Typeを使用してアップロードする 画像を説明しなければなりません
前に説明したPOSTリクエストとは異なり Contact-Lengthというフィールドが追加されます このフィールドを使用してアップロードする サムネイルのサイズはバイト単位で指定し その画像を表現するバイトで 構成されるブック体を指定します
Handout生成フローの過程において この画像はActivityを代表する 目的で使用されます したがってあなたのコンテンツを最も良く 代表する画像を指定するように留意してください 以上がサムネイルに対応する POSTエンドポイントの簡単な説明でした これに対応するGETとDELETEエンドポイントは 構造的によく似ています さらに詳しい内容については Apple Developerドキュメントをご覧ください 次へ移る前に サムネイルエンドポイントに関する何項目かの ガイドラインに注意を向けておきたいと思います まずサムネイルを表すには PNGまたはJPEGを使用します
次にサムネイルの大きさは 330x330ピクセルとします これがSchoolworkで使用する画像分解能です
最後にアップロードの順番は最初に コンテキスト 続いてサムネイルの順で行います サムネイルが迷子にならないようにするため この順番を守ってください サムネイルがどのコンテキストからも 参照されていない場合は そのサムネイルの アップロードリクエストが拒絶されます
この処理は同時にあるサムネイルを 最後に参照するコンテキストは 削除されていなければならないということを 意味します それに続いて該当するサムネイルも削除されます 次に進む前に 何か間違いが起こったときにAPIはどのように 反応するのかという問題について説明します エラーを報告しているサムネイルがあったとして それにPOSTしようとしたときに あなたが得るかもしれない応答の例を示します HTTPステータスコードが予期される訳ですが エラーを報告する応答にはこれとは別に 問題点を詳しく説明する JSONボディが含まれているはずです IDフィールドには一意の 識別子が記入されていますから これを使用してエラーを 同定して追跡することができます “code”フィールドを追ってみると 認証上の問題が発生していることが分かり
“message”フィールドを調べてみると そこには人間が読める型式で 問題が説明されており おまけに問題を解消する方法まで書いてあります エラーコードの 完全なリストと対応するメッセージが Apple Developerドキュメントとして 公開される予定です それではこの例が示す認証エラーは どう処置すればよいのでしょうか?
お約束したようにまずは認証について説明します 前にも触れましたように ClassKit Catalog APIにおける認証は JSON Web Tokenまたは単に JWTを使用して処理されます これは産業標準の1つであり Appleのいくつかのウェブサービスに またがって使用されています
まず始めとしてApple Developerポータルへ ログインしてから あなたのチームのClassKit Catalog APIキーを入力します
このプライベートキーは ClassKit Catalog APIとの認証照合に用いられる JWTを生成する目的で使用されますから あなたが何らかの リクエストを発行するときには必ず 前にも触れたAuthorizationの一部として 提出しなければなりません
JWTはヘッダーペイロード およびシグネチャと呼ばれる 3つの部分から構成されています
ヘッダーとペイロードを作成するために Apple Developerポータルに記載されている キーIDとチームIDを入力しなければなりません
これによってクレデンシャルが あなたの開発チームと関連付けられます さらにこのトークンを識別するUUIDと 2つのUNIXタイムスタンプが生成されます 一方のタイムスタンプは トークンの発行日時を表し 他方はトークンの失効日時を表します ここで私たちが見ているのは 整形前の生のフィールドです 最終的なトークンを形成するためには これらのフィールドをBase64で エンコードしなければなりません JWTを完成させるにはシグネチャが必要です シグネチャはエンコードされたヘッダーと エンコードされたペイロードから作成されます この署名で使用されるアルゴリズムが ECDSASHA256です この問題は複数のプログラム言語にまたがって 多数の文献が公表されていますから 処理の内容を理解するのは簡単です
この方法で完全に書式化された JWTは次のように見えます
Authorizationヘッダーはその一部として このトークンを含まなければならず その先頭には“Bearer”という プリフィックスが付けられています
これですべてのピースが揃いました それではアップロードしたコンテンツを ユーザーに提示する前に どのようにコンテンツを テストすればよいのでしょう? コンテンツを提示する環境には developmentとproductionの2つがあります
変更があったときにそのテストを行うのであれば “environment”クエリパラメータを 使用してコンテンツを development環境へアップロードします これはこのプレゼンの前の部分で示した方法です アップロードが完了したならば iOSの開発ビルドを実行している デバイス上でSettingsを開いて Developerタブへ移動します ClassKit APIをタップして 他のオプションを表示させます ClassKit Catalog Environmentの下にある Development environmentを選択します
設定が終わると ClassKitはデータの取り込み先を変更して あなたが選択した環境にしたがって 適正なコンテンツをSchoolworkに表示します
developmentへ送り出したコンテンツは Development環境を使用する すべてのClassKit Appleデベロッパーから 利用可能であることに注意してください
以上の説明のまとめとしてAPIを使用するときは 常に留意すべきベストプラクティスの いくつかを説明したいと思います
最初のかつ最も重要な事項として 新規コンテンツの定義および 古いコンテンツの削除を行うときは ClassKit Catalog APIを使用して この操作を報告してください これによりあなたのアプリケーションと そのActivitiesが Schoolworkで適正に表現されることが 保証されます 次にコンテンツ用に提供されている ロケールサポートを積極的に活用してください
これによりあなたのアプリケーションが最大限 広い範囲のユーザーに対応できるようになります
最後になりますがきっと皆さまは 報告するコンテキストの中でできるだけ詳しい 情報を提供したいと考えられたでしょうし コンテキストにサムネイルを 付属させたいと思われたのではないでしょうか これは理由のあることでSchoolworkを使用して ユーザーへ詳しい情報を提供できることに加え ユーザーがあなたのアプリケーションからの コンテンツを割り付け可能というのが重要な理由です 以上でClassKit Catalog APIの説明は終了です ClassKitデベロッパーの皆様には 今年の夏からこれらのAPIが提供されます 私たちのプレゼン“ClassKitに関する新機能” もここで終了とさせて頂きます ありがとうございました
-
-
6:25 - Add Thumbnail and Summary to Quiz Context
// Create a context for quiz let quizContext = CLSContext.init(type: CLSContextType.quiz, identifier: "science_Investigation_quiz", title: "Measurements Quiz") // Add a summary describing this context quizContext.summary = "A short quiz to test how much students know about scientific measurements and how to examine and analyze scientific data." // Add a thumbnail for this context — ClassKit will downsize thumbnails to 330 x 330 px if needed let bundle = Bundle.main if let resourceURL = bundle.resourceURL { let imageURL = resourceURL.appendingPathComponent("measurements_quiz.jpg") if let thumbnail = thumbnailFromImage(atURL: imageURL) { quizContext.thumbnail = thumbnail } }
-
6:52 - thumbnailFromImage
// Create a thumbnail of maximum dimension 330 x 330 px from an image file func thumbnailFromImage(atURL: URL) -> CGImage? { if let imageSource = CGImageSourceCreateWithURL(atURL as CFURL, nil) { let thumbnailOptions = [kCGImageSourceCreateThumbnailFromImageAlways as String: true, kCGImageSourceThumbnailMaxPixelSize as String: 330] return CGImageSourceCreateThumbnailAtIndex( imageSource, 0, thumbnailOptions as CFDictionary); } return nil }
-
7:59 - Add suggestedAge and suggestedCompletionTime
// Add suggested age range appropriate for the content — ages 9 to 11 years quizContext.suggestedAge = NSRange(9...11) // Add suggested time to complete this quiz — 15 to 20 minutes quizContext.suggestedCompletionTime = NSRange(15...20)
-
8:15 - Add progress reporting capabilities
// Add progress reporting capabilities let reportingPercentDetails = "Reports percentage of progress" let reportingCapabilityPercent = CLSProgressReportingCapability.init( kind: .percent, details: reportingPercentDetails) let reportingQuantityDetails = "Reports number of hints used" let reportingCapabilityQuantity = CLSProgressReportingCapability.init( kind: .quantity, details: reportingQuantityDetails) quizContext.addProgressReportingCapabilities([reportingCapabilityPercent, reportingCapabilityQuantity])
-
-
特定のトピックをお探しの場合は、上にトピックを入力すると、関連するトピックにすばやく移動できます。
クエリの送信中にエラーが発生しました。インターネット接続を確認して、もう一度お試しください。