Difference between revisions of "KiwixKolibri"

From Kiwix
Jump to navigation Jump to search
(added sample code that could be useful for Kiwix<-->Kolibri initegration on Android)
(More details for android integration between apps)
Line 77: Line 77:
# [https://tech.just-eat.com/2015/06/29/deep-linking-in-android-the-easy-way/ Article about ACTION_VIEWs] using a custom scheme
# [https://tech.just-eat.com/2015/06/29/deep-linking-in-android-the-easy-way/ Article about ACTION_VIEWs] using a custom scheme


From my limited understanding, we can define two custom `scheme`s such that:
We can define two custom `scheme`s such that:
  - ACTION_VIEW intents that start with `kolibri://<path>` will be handled by the Kolibiri app,
* ACTION_VIEW intents that start with `kolibri://<path>` will be handled by the Kolibiri app (see below)
  - and ACTION_VIEW intents starting with `kiwix://<path>` will be handled by the Kiwix app,
* ACTION_VIEW intents starting with `kiwix://<path>` will be handled by the Kiwix app,
 
* Suppose you're in the Kiwix app and you're browsing some videos from KA zim file. The exercises don't work within the Kiwix appthough, but you can click on an perseus exercise and the Kiwix app will send you to the Kolibri app as follows  Uri exercise = Uri.parse("kolibri:/learn/#/1ceff53605.../topics/c/845ce535...");<br> Intent callIntent = new Intent(Intent.ACTION_VIEW, exercise); // do check here callIntent.startActivity()
We could something like this in the Kolibri android app manifest need:
We could something like this in the Kolibri android app manifest:
  <nowiki>
   
    <activity
    <activity
        android:name=".activities.LinkDispatcherActivity"
        android:name=".activities.LinkDispatcherActivity"
        android:noHistory="true"
        android:noHistory="true"
        android:launchMode="singleInstance"
        android:launchMode="singleInstance"
        android:theme="@android:style/Theme.NoDisplay" >
        android:theme="@android:style/Theme.NoDisplay" >
        <intent-filter>
        <intent-filter>
            <action android:name="android.intent.action.VIEW"/>
            <action android:name="android.intent.action.VIEW"/>
            <category android:name="android.intent.category.DEFAULT"/>
            <category android:name="android.intent.category.DEFAULT"/>
            <category android:name="android.intent.category.BROWSABLE"/>
            <category android:name="android.intent.category.BROWSABLE"/>
            <data android:scheme="kolibri"/>
            <data android:scheme="'''kolibri'''"/>
            <data android:host="view_channel"/>
            '''<nowiki><data android:host="view_channel"/></nowiki>
            <data android:host="view_node"/>
            <nowiki><data android:host="view_node"/></nowiki>'''
            <data android:pathPattern=".*"/>
            <nowiki><data android:pathPattern=".*"/></nowiki>
        </intent-filter>
        </intent-filter>
    </activity>
    </activity>
</nowiki>


in the Kiwix android app
in the Kiwix android app
  <nowiki>
   
    <activity
    <activity
        android:name=".activities.LinkDispatcherActivity"
        android:name=".activities.LinkDispatcherActivity"
        android:noHistory="true"
        android:noHistory="true"
        android:launchMode="singleInstance"
        android:launchMode="singleInstance"
        android:theme="@android:style/Theme.NoDisplay" >
        android:theme="@android:style/Theme.NoDisplay" >
        <intent-filter>
        <intent-filter>
            <action android:name="android.intent.action.VIEW"/>
            <action android:name="android.intent.action.VIEW"/>
            <category android:name="android.intent.category.DEFAULT"/>
            <category android:name="android.intent.category.DEFAULT"/>
            <category android:name="android.intent.category.BROWSABLE"/>
            <category android:name="android.intent.category.BROWSABLE"/>
            <data android:scheme="kiwix"/>
            <data android:scheme="'''kiwix'''"/>
            <data android:host="view_zimfile"/>
            '''<nowiki><data android:host="view_zimfile"/></nowiki>
            <data android:host="view_page"/>
            <nowiki><data android:host="view_page"/></nowiki>'''
            <data android:pathPattern=".*"/>
            <nowiki><data android:pathPattern=".*"/></nowiki>
        </intent-filter>
        </intent-filter>
    </activity>
    </activity>
</nowiki>
To verify there is an activity available that can respond to the intent, call <code>queryIntentActivities()</code> to get a list of activities capable of handling your <code>Intent</code>. If the returned <code>List</code> is not empty, you can safely use the intent. For example:
PackageManager packageManager = <code>getPackageManager()</code>;<br>
List = activities = packageManager.queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY);
boolean isIntentSafe = activities.size() > 0;
If <code>isIntentSafe</code> is <code>true</code>, then we know that the intent-receiving app is installed and will respond to the intent.


== Stickers & Swag ==
== Stickers & Swag ==

Revision as of 14:34, 26 July 2017

Introduction

This page is about integration between Kiwix and Kolibri [1] [2] [3]

(created for the Wikimania 2017 Hackathon)

Trying Kolibri

Online demo: http://kolibridemo.learningequality.org/

Please note that Kolibri is alpha software - we do not recommend deploying it before later this year. Also, please do not share/promote it externally yet, as we are still stabilizing it and streamlining the UX for public usability.

Using locally:

  1. Download the latest .pex release: https://github.com/learningequality/kolibri/releases
  2. Make the file executable: chmod +x kolibri-v0.4.3.pex
  3. Run Kolibri ./kolibri-v0.4.3.pex start
  4. Navigate with your browser to http://localhost:8080

Once installed, you can add content by logging in as an administrator and using one of the many available Channel IDs... these are just a few of them, we should be able to have more

Khan Academy small test:      8b4d3e6d3d4842ba8ea658335b5dd252
Khan Academy English Math:    1ceff53605e55bef987d88e0908658c5
Khan Academy Swahili Math:    ec164fee25ee526296e68f7c10b1e169
Khan Academy with exercises:  f6d2f857af2e304093648daf2d8cacec
PhET Interaction Simulations: 197934f144305350b5820c7c4dd8e194
CK-12:                        1d8f6d84618153c18c695d85074952a7
MIT Blossoms:                 913efe9f14c65cb1b23402f21f056e99
Sikana in Chinese (ZH):       3e9ffc29aa0b59c3bda8d8c7ed179685
Sikana in French (FR):        8ef625db6e86506c9a3bac891e413fff
Sikana in English (EN):       3e464ee12f6a50a781cddf59147b48b1

In case you find an issue, feel free to ask in the community forum or file an issue on Github.

Integration focus areas

Cross-linking between platforms

Shallow-linking

From Kolibri: detect that Kiwix is installed, get an index of OpenZIM bundles and their metadata, and show links to the corresponding Kiwix URLs alongside the Kolibri channel list

From Kiwix: _____

Deep-linking

A more general version of cross-linking to resources between the platforms. Possibly based either on a GUID or URI approach (which will likely be implemented in some form for cross-linking within Kolibri channels anyway), or through shared metadata/tagging schemes.

From Kiwix: Say you export a zim of a Kolibri channel which has an exercise, then we can use a placeholder with a deep link back to Kolibri.

From Kolibri: Instead of trying to fit in a Wikipedia zim, we can find a mechanism to add links as related contents. Like "Want to learn more about atomic fusion, read about it on Wikipedia".

Importing/Exporting content

Exporting Kolibri channels to Zim

Static contents like videos in Khan Academy or Sikana.tv can be exported as a static zim, given we use the meta data (topic trees) for navigation + some template parameters like title, logo and colors.

Importing from a Zim into a Kolibri channel

Importing a Zim into a channel in the Kolibri Content Curation server: Build a "sushi chef" script (using the ricecooker) to create a topic tree by traversing the content within the Zim. Depending on the format of the content in the zim, this might be a topic tree with videos, or in the Kolibri "HTML5 app" format, a set of pages that will be iframed. May not be very useful for something like all of Wikipedia, but can be useful for smaller Zim projects (or ones with a lot of rich media files).

  • Benefit: Someone can start creating exercises and re-organizing for a specific educational purpose
  • Benefit: Other channels can include new learning materials from already existing Zim resources

Shared OPDS standard

Aligning standards of exporting meta data to OPDS, such that Kiwix Zim resources and Kolibri Channels can be searched and browsed through the same interfaces. Collaborate with Tim Moody on this.

Integration on Android

Using Intents to cross-link between the Kolibri and Kiwix apps. Useful links:

  1. Intent basics
  2. Intent class
  3. intent-filters
  4. list of "common" intents, for example Camera
  5. we're interested in the ACTION_VIEW intent: ACTION VIEW, the view's URI can be resolved with a custom schema
  6. Article about ACTION_VIEWs using a custom scheme

We can define two custom `scheme`s such that:

  • ACTION_VIEW intents that start with `kolibri://<path>` will be handled by the Kolibiri app (see below)
  • ACTION_VIEW intents starting with `kiwix://<path>` will be handled by the Kiwix app,
  • Suppose you're in the Kiwix app and you're browsing some videos from KA zim file. The exercises don't work within the Kiwix appthough, but you can click on an perseus exercise and the Kiwix app will send you to the Kolibri app as follows Uri exercise = Uri.parse("kolibri:/learn/#/1ceff53605.../topics/c/845ce535...");
    Intent callIntent = new Intent(Intent.ACTION_VIEW, exercise); // do check here callIntent.startActivity()

We could something like this in the Kolibri android app manifest:

    <activity
        android:name=".activities.LinkDispatcherActivity"
        android:noHistory="true"
        android:launchMode="singleInstance"
        android:theme="@android:style/Theme.NoDisplay" >
        <intent-filter>
            <action android:name="android.intent.action.VIEW"/>
            <category android:name="android.intent.category.DEFAULT"/>
            <category android:name="android.intent.category.BROWSABLE"/>
            
            <data android:host="view_channel"/>
            <data android:host="view_node"/>
            <data android:pathPattern=".*"/>
        </intent-filter>
    </activity>

in the Kiwix android app

    <activity
        android:name=".activities.LinkDispatcherActivity"
        android:noHistory="true"
        android:launchMode="singleInstance"
        android:theme="@android:style/Theme.NoDisplay" >
        <intent-filter>
            <action android:name="android.intent.action.VIEW"/>
            <category android:name="android.intent.category.DEFAULT"/>
            <category android:name="android.intent.category.BROWSABLE"/>
            
            <data android:host="view_zimfile"/>
            <data android:host="view_page"/>
            <data android:pathPattern=".*"/>
        </intent-filter>
    </activity>

To verify there is an activity available that can respond to the intent, call queryIntentActivities() to get a list of activities capable of handling your Intent. If the returned List is not empty, you can safely use the intent. For example:

PackageManager packageManager = getPackageManager();
List = activities = packageManager.queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY); boolean isIntentSafe = activities.size() > 0;

If isIntentSafe is true, then we know that the intent-receiving app is installed and will respond to the intent.

Stickers & Swag

  1. Kolibri <3 Kiwix (Lovebirds :) )


References