<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Craig Oda</title>
    <description>The latest articles on DEV Community by Craig Oda (@codetricity).</description>
    <link>https://dev.to/codetricity</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F215076%2F28e27113-deb0-44a0-86da-ff5e662d5951.png</url>
      <title>DEV Community: Craig Oda</title>
      <link>https://dev.to/codetricity</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/codetricity"/>
    <language>en</language>
    <item>
      <title>How to Set Up Django With Central OAuth2 Login</title>
      <dc:creator>Craig Oda</dc:creator>
      <pubDate>Thu, 24 Oct 2019 20:52:48 +0000</pubDate>
      <link>https://dev.to/codetricity/how-to-set-up-django-with-central-oauth2-login-1co</link>
      <guid>https://dev.to/codetricity/how-to-set-up-django-with-central-oauth2-login-1co</guid>
      <description>&lt;p&gt;I recently set up 10 Django servers to use the same Google G Suite corporate email login. This allows everyone in a company to log into all the Django and Discourse servers with the same email and password. This solution will also work with social logins from many providers such as Twitter, Facebook, GitHub. You can also use identity management solutions such as Auth0, Okta and OneLogin.&lt;/p&gt;

&lt;p&gt;Although I assumed the task would be quick and easy, I ran into several challenges with outdated online examples.  I’ll explain what I did for deployment with Django 2.2, Python 3.7 and social-app-django 3.1.&lt;/p&gt;

&lt;p&gt;Before standardizing on Google OAuth2, I deployed with Auth0.  Although the deployment was easy, users ran into problems with password resets using the Auth0 interface and there was no easy way to get support or ask questions to Auth0 during my assessment period.  I decided to drop Auth0 for the initial deployment and go with Google. &lt;/p&gt;

&lt;p&gt;The staff managing the content and users on all the Django and Discourse servers were already using Google email and therefore all staff had a Google account.&lt;/p&gt;

&lt;p&gt;A GitHub repository of this example project is available &lt;br&gt;
&lt;a href="https://github.com/codetricity/django-social-login-example" rel="noopener noreferrer"&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Begin this tutorial after you have your Django project and app started.&lt;/p&gt;
&lt;h2&gt;
  
  
  Background
&lt;/h2&gt;

&lt;p&gt;The screenshots and servers used in this example, are from the &lt;a href="https://community.theta360.guide/" rel="noopener noreferrer"&gt;RICOH THETA Developer Community&lt;/a&gt; infrastructure run by &lt;a href="https://oppkey.host/" rel="noopener noreferrer"&gt;Oppkey Host&lt;/a&gt;. We initially started with local logins on Discourse servers and one-off web sites. As the number of servers grew, we ran into management problems.  We decided to standardize on Google OAuth2 due to simplicity of deployment.&lt;/p&gt;

&lt;p&gt;A management interface allows content and user management staff from different companies to access the admin interface for many servers from different communities with the same email and password. Authorized servers are stored in a Profile object that extends the standard User object in Django.  In addition to Django servers, staff log into and manage Discourse servers using the same dashboard.&lt;/p&gt;

&lt;p&gt;To keep this tutorial simple, the management interface is not shown in this tutorial.&lt;/p&gt;
&lt;h2&gt;
  
  
  Setup
&lt;/h2&gt;
&lt;h3&gt;
  
  
  Install Social Auth
&lt;/h3&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;$ pip install social-auth-app-django
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;Or&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;$ pipenv install social-auth-app-django
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;h3&gt;
  
  
  console.developers.google.com
&lt;/h3&gt;

&lt;p&gt;Go to https//console.developers.google.com and create new credentials.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2Flqxcjit4j2u0mnr8c3xl.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2Flqxcjit4j2u0mnr8c3xl.png" alt="Alt Text"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F5n0cmrjvsibdfsxfcu1i.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F5n0cmrjvsibdfsxfcu1i.png" alt="Alt Text"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2Fygg06rabktwnozhm9rmx.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2Fygg06rabktwnozhm9rmx.png" alt="Alt Text"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Select Web application.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F4vxt374nnnxow0igweu6.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F4vxt374nnnxow0igweu6.png" alt="Alt Text"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F1zu8uddjlwfcyxnrbzjy.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F1zu8uddjlwfcyxnrbzjy.png" alt="Alt Text"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Under Authorized redirect URIs, add the following:&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;http://localhost:8000/complete/google-oauth2/
https://project-domain.com/complete/google-oauth2/
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;Replace &lt;code&gt;project-domain.com&lt;/code&gt; with the URL of your project server.&lt;/p&gt;
&lt;h2&gt;
  
  
  Settings.py
&lt;/h2&gt;


&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="c1"&gt;# social auth configuration
&lt;/span&gt;
&lt;span class="n"&gt;AUTHENTICATION_BACKENDS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;social_core.backends.google.GoogleOAuth2&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;django.contrib.auth.backends.ModelBackend&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;LOGIN_URL&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;/auth/login/google-oauth2/&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;

&lt;span class="n"&gt;LOGIN_REDIRECT_URL&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;/manage/&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;
&lt;span class="n"&gt;LOGOUT_REDIRECT_URL&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;/&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;
&lt;span class="n"&gt;SOCIAL_AUTH_URL_NAMESPACE&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;social&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;


&lt;span class="n"&gt;INSTALLED_APPS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
    &lt;span class="bp"&gt;...&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;social_django&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;
    &lt;span class="bp"&gt;...&lt;/span&gt;
&lt;span class="p"&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;create a new file called &lt;code&gt;local_settings.py&lt;/code&gt; and insert the following at the bottom of the &lt;code&gt;settings.py&lt;/code&gt; file to create a connection from &lt;code&gt;settings.py&lt;/code&gt; to &lt;code&gt;local_settings.py&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;try&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;.local_settings&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;
&lt;span class="k"&gt;except&lt;/span&gt; &lt;span class="nb"&gt;ImportError&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="k"&gt;pass&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  local_settings.py
&lt;/h2&gt;

&lt;p&gt;Put the values from Google into the constants below.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;SOCIAL_AUTH_GOOGLE_OAUTH2_KEY&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;GOOGLE_KEY&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;
&lt;span class="n"&gt;SOCIAL_AUTH_GOOGLE_OAUTH2_SECRET&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;SECRET&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  urls.py
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from django.contrib.auth.views import LogoutView
from django.urls import include

...

urlpatterns = [
path('admin/', admin.site.urls, name='administrator'),
path('', include('social_django.urls', namespace='social')),
path('', views_main.index, name='index'),
path(
    'logout/',
    LogoutView.as_view(template_name=settings.LOGOUT_REDIRECT_URL),
    name='logout'
    ),
path('manage/', views.manage, name='manage'),
]

views.py
def manage(request):
    return render(request, 'manage.html')

template manage.html
The snippet below uses Bootstrap for styling.
&amp;lt;div class="container pt-5"&amp;gt;
        &amp;lt;h1&amp;gt;THETA Dream and Build Management Dashboard&amp;lt;/h1&amp;gt;

        {% if user.is_authenticated %}

        &amp;lt;h2&amp;gt;
            &amp;lt;a href="/admin/"&amp;gt;    Go To Dashboard&amp;lt;/a&amp;gt;

        &amp;lt;/h2&amp;gt;
        &amp;lt;hr&amp;gt;

        &amp;lt;a class="btn btn-primary mt-5" href="{% url 'logout' %}"&amp;gt;Logout&amp;lt;/a&amp;gt;

        {% else %}
        &amp;lt;a class="btn btn-primary" href="{% url 'social:begin' 'google-oauth2' %}"&amp;gt;
                Login
                &amp;lt;/a&amp;gt;
        {% endif %}
    &amp;lt;/div&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;make and migrate models&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;$ python manage.py makemigrations 
$ python manage.py migrate
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;run server and test&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;$ python manage.py runserver
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2Fj78so4wc6iv1yz2bamvb.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2Fj78so4wc6iv1yz2bamvb.png" alt="Alt Text"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F2ni5siswdtzwfnss3ygz.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F2ni5siswdtzwfnss3ygz.png" alt="Alt Text"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2Fm9ln71gvrs0p8dwyn5su.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2Fm9ln71gvrs0p8dwyn5su.png" alt="Alt Text"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Summary
&lt;/h2&gt;

&lt;p&gt;Although there are many ways to set up centralized login for different web applications, using Google OAuth2 is simple and well-documented.  If you’ve been hesitant to move off of local logins, it’s a great time to look at the available solutions.&lt;/p&gt;

&lt;p&gt;Related Topics Not Covered in This Tutorial&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://meta.discourse.org/t/configuring-google-login-for-discourse/15858" rel="noopener noreferrer"&gt;Configuring Google login for Discourse&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://auth0.com/blog/django-tutorial-building-and-securing-web-applications/" rel="noopener noreferrer"&gt;Django Tutorial: Building and Securing Web Applications&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>django</category>
    </item>
    <item>
      <title>360 Image Viewers for Web Developers
</title>
      <dc:creator>Craig Oda</dc:creator>
      <pubDate>Fri, 23 Aug 2019 02:04:53 +0000</pubDate>
      <link>https://dev.to/codetricity/360-image-viewers-for-web-developers-bp4</link>
      <guid>https://dev.to/codetricity/360-image-viewers-for-web-developers-bp4</guid>
      <description>&lt;p&gt;Almost every developer working with 360 images will build a web site to share their 360 images at some point.  This might only be for testing or to share with team members, but it could also be to show clients or customers.&lt;/p&gt;

&lt;p&gt;Fortunately, there are many pre-built libraries and services to display 360 images in your custom web site.&lt;/p&gt;

&lt;p&gt;A growing list of viewers is available here:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://gallery.theta360.guide/viewers/"&gt;https://gallery.theta360.guide/viewers/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I'll include a list of 12 popular viewers below.  Thanks to &lt;a href="https://community.theta360.guide/u/egene/summary"&gt;eGene&lt;/a&gt; &lt;br&gt;
of &lt;a href="https://360photo-to-video.com/"&gt;360 Photo to Video Online Converter&lt;/a&gt; &lt;br&gt;
for getting this list started. &lt;/p&gt;

&lt;h2&gt;
  
  
  Pannellum
&lt;/h2&gt;

&lt;p&gt;Pannellum is a free open source panorama and 360° viewer. It's small, fast, easy to use. Though pretty basic, it has an interesting feature — multires panoramas (ability to use images with different resolution depending on zoom for single panorama). It claims to work in all modern browsers with WebGL support. Mobile browsers are not officially supported, so they may or may not work properly.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;License: MIT License &lt;/li&gt;
&lt;li&gt;Price: free &lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/mpetroff/pannellum"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Marzipano
&lt;/h2&gt;

&lt;p&gt;Developed by a company acquired by Google, then open sourced, this powerful viewer offers plenty of features, including wizard tool to help you enable options that you need. It supports all major desktop and mobile browsers (and has Flash version for legacy), provides powerful Javascript API for you to build custom applications.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular, cube &lt;/li&gt;
&lt;li&gt;License: Apache License 2.0 &lt;/li&gt;
&lt;li&gt;Price: free &lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.marzipano.net/"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Photo Sphere Viewer
&lt;/h2&gt;

&lt;p&gt;Photo Sphere Viewer is a comprehensive JavaScript library that allows you to display panoramic images. It's based on Three.js and shows good performance on WebGL enabled browsers with fallback to canvas for older browsers. It also supports touch screens. Other cool features include cropped (incomplete) panorama support and support of various types of markers (polygons, polylines, html, images, SVGs).&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;License: MIT License &lt;/li&gt;
&lt;li&gt;Price: free &lt;/li&gt;
&lt;li&gt;&lt;a href="https://photo-sphere-viewer.js.org/"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  360 Image Viewer
&lt;/h2&gt;

&lt;p&gt;It's a basic panorama viewer that doesn't have lots of features, but it still can work for you depending on your needs as it does the job. Some settings include: field of view, rotation speed, damping and that's pretty much all. It provides ability to set a callback function on frame change, so some customization is possible. Please note that its navigation mode is different from some other viewers: it uses what is called QTVR style when to navigate the image you need to press mouse button and move the cursor (and it can't be changed to "drag" style). Check it out below or on their demo page to see if you are comfortable with it.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;License: MIT License &lt;/li&gt;
&lt;li&gt;Price: free &lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/Jam3/360-image-viewer"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Kaleidoscope
&lt;/h2&gt;

&lt;p&gt;An embeddable, lightweight, dependency-free 360º image and video viewer. Works in all modern browsers. Some basic options and methods available for custom integrations. Check out video demo on their demo page.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;License: Apache License 2.0 &lt;/li&gt;
&lt;li&gt;Price: free &lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/thiagopnts/kaleidoscope"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Panolens
&lt;/h2&gt;

&lt;p&gt;Another Javascript panorama viewer based on Three.js with impressive set of features. Equirectangular and cube images, google street view images, annotations (markers) and more. Supports 360° videos. Ability to create interactive tours. Codepen playgrounds available on their website.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular, cube &lt;/li&gt;
&lt;li&gt;License: MIT License &lt;/li&gt;
&lt;li&gt;Price: free &lt;/li&gt;
&lt;li&gt;&lt;a href="https://pchen66.github.io/Panolens/"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  360player.io
&lt;/h2&gt;

&lt;p&gt;Most of the paid viewers (including this one) offer integration with your website with an iframe. That means no coding/installation required, all configuration is done with their online tools and you only need to embed add iframe to your pages. 360player.io offers a nice looking easy to use viewer that works in all modern (supporting WebGL) and most legacy and mobile browsers. Automatic image recognition, labeling and geo-tagging included. Prices start at $12/month (no free tier).&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;Price: from $12/month with unlimited uploads an &lt;/li&gt;
&lt;li&gt;&lt;a href="https://360player.io/"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Panoraven
&lt;/h2&gt;

&lt;p&gt;Commercial 360° photo viewer with a free plan for personal use. And you don't have to register to try it. You would have to register only if you need it for commercial use or want to manage your photos and customize viewers. Please note that the plan also defines your bandwidth limit, so make sure you choose one appropriate for your needs. Integration is done with an iframe.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;Price: from $15/month with unlimited uploads. F &lt;/li&gt;
&lt;li&gt;&lt;a href="https://panoraven.com/en"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Kuula
&lt;/h2&gt;

&lt;p&gt;Kuula positions their viewer as a tool for creating 360° virtual tours. It means your can add labels, hotspots, audio (and more) to your images. Mobile browsers are supported. Free tier is limited to 100 uploads per month, and they are public (actually displayed on their website), so be careful with what you upload.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;Price: from $12/month (with annual subscription &lt;/li&gt;
&lt;li&gt;&lt;a href="https://kuula.co/"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Momento 360
&lt;/h2&gt;

&lt;p&gt;This photo and video viewer offers virtual tours and albums creation and has integration with multiple CMS and blogging platforms. Links created by Momento 360 are shareable, meaning you can send them to your friends and they will be able to interact with your 360° content on Momento's website. Generic iframe integration is also available. Free tier is limited to 2GB storage with Momento360 branding. Cheapest plan is $4.99 a month (when billed annually), but surprise, it will also have Momento's branding enforced ¯_(ツ)_/¯. You'd need to pay at least $15 per month to turn that off.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;Price: from $4.99/month (with annual subscripti &lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.momento360.com/"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  A-Frame
&lt;/h2&gt;

&lt;p&gt;A-Frame is a web framework for building virtual reality (VR) experiences. A-Frame is based on top of HTML, making it simple to get started. But A-Frame is not just a 3D scene graph or a markup language; the core is a powerful entity-component framework that provides a declarative, extensible, and composable structure to three.js. Works on Vive, Rift, Daydream, GearVR, desktop.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;License: MIT License &lt;/li&gt;
&lt;li&gt;Price: free &lt;/li&gt;
&lt;li&gt;&lt;a href="https://aframe.io/"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Theasys
&lt;/h2&gt;

&lt;p&gt;Powerful and sophisticated 360° Virtual Tour building platform. Includes VR Editor Features, Embed &amp;amp; Customization Options, Advanced Embed Options, Security &amp;amp; Performance, and more.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Supported projections: equirectangular &lt;/li&gt;
&lt;li&gt;Price: free &lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.theasys.io/"&gt;More Information&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>webdev</category>
    </item>
    <item>
      <title>360 Image Database for Face Object Detection</title>
      <dc:creator>Craig Oda</dc:creator>
      <pubDate>Mon, 19 Aug 2019 23:41:44 +0000</pubDate>
      <link>https://dev.to/codetricity/360-image-database-for-face-object-detection-4mgm</link>
      <guid>https://dev.to/codetricity/360-image-database-for-face-object-detection-4mgm</guid>
      <description>&lt;p&gt;TensorFlow is a great platform for experimentation with learning models.  About a year ago, I did some experiments with using the TensorFlow samples inside of the RICOH THETA 360 camera.  A GitHub repo of the &lt;a href="https://github.com/codetricity/tensorflow-theta"&gt;samples&lt;/a&gt; is available to you to experiment with if you have a RICOH THETA V or Z1. You can also run the standard demos on an Android phone or AVD.&lt;/p&gt;

&lt;p&gt;The main problem using the TensorFlow demos with a 360 camera was detection of objects in an equirectangular image. In the example below, you can see that the 360 image viewed in equirectangular format distorts the faces.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--Z7INw5wF--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://i.imgur.com/54KbYD8.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--Z7INw5wF--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://i.imgur.com/54KbYD8.jpg" alt="equirectangular"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This makes it challenging to access an image network such as YOLO (You Only Look Once).&lt;/p&gt;

&lt;p&gt;Recently, developer Amine Amri, put out a &lt;a href="https://community.theta360.guide/t/theta-auto-trigger-plug-in-by-amine-amri/4665?u=codetricity"&gt;project&lt;/a&gt; that introduced me to FDDB-360, a dataset derived from Face Detection Dataset and Benchmark &lt;a href="http://viswww.cs.umass.edu/fddb/"&gt;FDDB&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;FDDB-360 contains 17,052 fisheye-looking images and a total of 26,640 annotated faces.&lt;/p&gt;

&lt;p&gt;The dataset is available from &lt;a href="http://www.sfu.ca/%7Eibajic/#data"&gt;http://www.sfu.ca/~ibajic/#data&lt;/a&gt; (J. Fu, S. R. Alvar, I. V. Bajić, and R. G. Vaughan,“FDDB-360: Face detection in 360-degree fisheye images,” Proc. IEEE MIPR’19 ,San Jose, CA, Mar. 2019).&lt;/p&gt;

&lt;h2&gt;
  
  
  Working Without 360 Image DB
&lt;/h2&gt;

&lt;p&gt;The TensorFlow demos work surprisingly well with 360 images without modification if the face is in the middle of the vertical height of the image.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--V2uE-R9z--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://i.imgur.com/OsumeHY.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--V2uE-R9z--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://i.imgur.com/OsumeHY.png" alt="face"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;You can even detect and blur faces close to a stitch line as long as the face is in the center of the vertical height.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--d383kKlN--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://i.imgur.com/pJEhZfw.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--d383kKlN--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://i.imgur.com/pJEhZfw.jpg" alt="edge face"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  When to use a 360 image DB of faces
&lt;/h2&gt;

&lt;p&gt;Your recognition will decrease when the face is captured above or below the center of the vertical height.  The higher or lower it is, the more distortion you will experience.  For the best chance of face detection, you should use a 360 image DB.&lt;/p&gt;

&lt;h2&gt;
  
  
  Next Steps
&lt;/h2&gt;

&lt;p&gt;If you want to join the discussion around using TensorFlow with the RICOH THETA and 360 images, please check out &lt;a href="https://community.theta360.guide/t/tensorflow-apk-for-theta-v-speech-object-detection-stylized-filters/3812?u=codetricity"&gt;Tensorflow apk for THETA V - Speech, object detection, stylized filters&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>tensorflow</category>
    </item>
  </channel>
</rss>
