Displaying Charts on Lightbox

Susper displayed charts which shows graphical representation of Result Frequency and Protocol Distribution(http or https). But since results from these charts added little value it was decided to display charts on a click of a button on a lightbox. (Issue: https://github.com/fossasia/susper.com/issues/1066 ). In this blog,I will describe how I have implemented charts on lightbox.

Uniting the graphs(Line and Bar Graph) in a same class:

Before beginning the implementation of lightbox, we should unite all the components that will be displayed on lightbox in a single class.

Here I have put the different types of charts in a class named graph.

<div class="graph large"> <div class="linegraph"><canvas baseChart
           [datasets]="lineChartData"
           [labels]="lineChartLabels"
           [options]="lineChartOptions"
           [chartType]="lineChartType"
           [colors]="lineChartColors"
></canvas></div><div class="bargraph"><canvas baseChart
           [datasets]="barChartData"
           [labels]="barChartLabels"
           [options]="barChartOptions"
           [chartType]="barChartType"
           [colors]="lineChartColors"
   ></canvas></div></div>

Implementing button to toggle display of light box:

To show and hide lightbox along with charts we must have a button.

Clicking on which should trigger a function which will internally execute the logic in typescript file to show and hide the lightbox.

<button class="btn" id="toggle-chart-button" (click)="BoxToggle()">
           {{analyticsStatus}} Analytics
 </button>

Creating a translucent black background:

Now to have a black overlay for lightbox we need a div element and inside it we need a closing button.

Clicking on the black overlay should toggle status of light box therefore we have binded click event with BoxToggle() method.

<div id="fade" class="black_overlay" (click)='BoxToggle()'><a class="closeX" id="closeX">&#10006;</a></div>

Creating a white block to display charts:

Now after creating a black overlay in background we need a white foreground to display charts.

Therefore I have implemented a div element and put all the chart elements inside the div element so that it will be displayed on a white foreground on a translucent black background.

<div id="light" class="white_content">
<div class="graph large"><div class="linegraph"><canvas baseChart
           [datasets]="lineChartData"
           [labels]="lineChartLabels"
           [options]="lineChartOptions"
           [chartType]="lineChartType"
           [colors]="lineChartColors"
   ></canvas></div>
<div class="bargraph"><canvas baseChart
           [datasets]="barChartData"
           [labels]="barChartLabels"
           [options]="barChartOptions"
           [chartType]="barChartType"
           [colors]="lineChartColors"
   ></canvas></div></div></div>

CSS for all above elements:

All the CSS which is written for charts, toggle button, white block and black overlay

To make it look attractive and similar to market leader can be found here.

Implementing the logic in typescript file:

Now we have created all the elements in frontend to display the lightbox but we need a little logic to show and hide the lightbox on clicking the button. For this I have used a variable analyticsStatus which is a string and is initialised with value ‘Show Chart’. Its value is displayed on the toggle button. I have used this variable with BoxToggle() function for implementing the logic for showing and hiding the lightbox.

This function checks the status of message and toggles it along with toggling lightbox with some javascript code. The code for the function is here.

BoxToggle() { if (this.analyticsStatus === 'Show Chart') {
     this.analyticsStatus = 'Hide Chart';
     document.getElementById('light').style.display = 'block';
     document.getElementById('fade').style.display = 'block';
   } else {
     this.analyticsStatus = 'Show Chart';
     document.getElementById('light').style.display = 'none';
     document.getElementById('fade').style.display = 'none'; }}

Resources

1.Creating a lightbox: https://www.emanueleferonato.com/2007/08/22/create-a-lightbox-effect-only-with-css-no-javascript-needed/

2.W3School lightbox: https://www.w3schools.com/howto/howto_js_lightbox.asp

3.Angular 2 Lightbox: https://lokeshdhakar.com/projects/lightbox2/

Continue Reading

Refactor of Dropdown Menu in Susper

The first version of the Susper top menu was providing links to resources and tutorials. In the next version of the menu, we were looking for a menu with more colorful icons, a cleaner UI design and a menu that should appear on the homepage as well. In this blog, I will discuss about refactoring the dropdown menu. This is how earlier dropdown of Susper looks like:

We decided to create a separate component for the menu DropdownComponent.

At first, I created a drop down menu with matching dimensions similar to what Google follows. Then, I gave padding: 28px to create similar UI to market leader. This will make a dropdown menu with clean UI design. I replaced the old icons with colorful icons. In the dropdown we have:

  • Added more projects of FOSSASIA like eventyay, loklak, susi and main website of FOSSASIA. Here how it looks now :

The main problem I faced was aligning the content inside the dropdown and they should not get disturbed when the screen size changes.
I kept the each icon dimensions as 48 x 48 inside drop down menu. I also arranged them in a row. It was easy to use div element to create rows rather than using ul and li tags which were implemented earlier.

To create a horizontal grey line effect, I used the hr element. I made sure, padding remained the same above and below the horizontal line.

At the end of drop down menu, @mariobehling suggested instead of writing ‘more’, it should redirect to projects page of FOSSASIA.

This is how I worked on refactoring drop down menu and added it on the homepage as well.

Resources

Continue Reading

Building interactive elements with HTML and javascript: Interact.js + resizing

{ Repost from my personal blog @ https://blog.codezero.xyz/building-interactive-elements-with-html-and-javascript-interact-js-resizing/ }

In a few of the past blog posts, we saw about implementing resizing with HTML and javascript. The functionality was pretty basic with simple resizing. In the last blog post we saw about interact.js.

interact.js is a lightweight, standalone JavaScript module for handling single-pointer and multi-touch drags and gestures with powerful features including inertia and snapping.

Getting started with Interact.js

You have multiple option to include the library in your project.

  • You can use bower to install (bower install interact) (or)
  • npm (npm install interact.js) (or)
  • You could directly include the library from a CDN (https://cdnjs.cloudflare.com/ajax/libs/interact.js/1.2.6/interact.min.js).
Implementing resizing

Let’s create a simple box using HTML. We’ll add a class called resizable to it so that we can reference it to initialize Interact.js

<div class="resizable">  
    Use right/bottom edge to resize
</div>

We need to create an interact instance. Once the instance is created, we have to call the resizable method on it to add resize support to the div.

interact('.resizable')
  .resizable({
    edges: { right: true, bottom: true }
  })
  .on('resizemove', function (event) {
    

  });

Inside the resizable method, we can pass configuration options. The edgesconfig key allows us to specify on which all edges, resizing should be allowed. Right now, we have allowed on the right and bottom edges. Similarly we can have resizing support in the top and left edges too.

The resizemove event is triggered by interact every time the user tries to resize the div. From the event, we can get the box that is being resized, (i.e) the target by accessing event.target.

The event object also provides us event.rect.width and event.rect.height which is the width and height of the div after resizing. We’ll not set this as the width of the div so that, the user is able to see the width change.

var target = event.target;
    // update the element's style
    target.style.width  = event.rect.width + 'px';
    target.style.height = event.rect.height + 'px';

We can also instruct Interact.js to preserve the aspect ratio of the box by adding an option preserveAspectRatio: true to the configuration object passed to resizable method during initialization.

JavaScript
interact('.resizable')
  .resizable({
    edges: { right: true, bottom: true }
  })
  .on('resizemove', function (event) {
    var target = event.target;

    // update the element's style
    target.style.width  = event.rect.width + 'px';
    target.style.height = event.rect.height + 'px';
  });

Resizing and drag-drop (with Interact.js) were used to create the Scheduler tool at Open Event. The tool allows event/track organizers to easily arrange the sessions into their respective rooms by drag-drop and also to easily change the timings of the events by resizing the event block. The entire source code of the scheduler can be viewed at app/static/js/admin/event/scheduler.js in the Open Event Organizer server’s GitHub repository.

Demo:
https://jsfiddle.net/xdfocdty/

Continue Reading

Update Fields with Array Input

Screenshot from 2016-07-15 17:57:58.png

There are certain fields in form where instead of a single value, we need an array of values to be stored. This are fields under the same category but having multiple elements, e.g., Tracks, Session Types, Microlocations, Sponsors, Social Links and similar such fields. Now as we know the way of doing this using simple html is provide the <input> tag with property “name” as “<field_name>[]”. So suppose we want to save the names of the mutliple tracks, we will have something like this
Screenshot from 2016-07-15 18:02:09.png

But the problem begins when you want to update name of a particular element (in this case Track). How to do it? Should we delete and create entries again? That doesn’t sound too good, does it? So what should we do? Let’s see….

Continue Reading

Handling file uploading in HTML5 and Express

The Open Event Webapp Generator has a pure HTML front end form, and Express based backend.

 

We needed an option where users can upload their own JSON files to create a schedule page for it.

On the HTML form that’s easy. As you can see here we simple add input tags with type=”file”


<input type="file" name="sponsorfile" id="sponsorfile">

In our express app, we need to use multer to be able to handle file uploads.

We create a middleware called uploadedFiles, and pass the middleware to the get() block

 

var express = require('express');
var multer = require('multer');
var app = express();

var upload = multer({dest: 'uploads/'});

var uploadedFiles = upload.fields([
  {name: 'speakerfile', maxCount: 1},
  {name: 'sessionfile', maxCount: 1},
  {name: 'trackfile', maxCount: 1},
  {name: 'sponsorfile', maxCount: 1},
  {name: 'eventfile', maxCount: 1},
  {name: 'locationfile', maxCount: 1}
]);

app.post('/live', uploadedFiles, function(req, res) {
         // req.files has the files
         // req.body has the POST body params
  });
});

Now we can access the files inside req.files (that will have a path to the temporary location of the file, you’ll have to use some filesystem module to read the files)

Continue Reading

Transmitting response from a Web page to a server.

{ Re-post from my Medium Post }

My project has pivoted from a standalone android app to a Web page that will generate a custom app for an event organizer’s use.

Read up here on what my project actually is.

So obviously some changes at the server are to be made to make this possible.

How are you planning to do it?

First of we started by providing a Web page that the organizers can use to submit information about the app they need to be built like the App’s name, the link to the API (for fetching the json files) and their email address (for mailing them the apk once it’s generated).

The HTML file for the same can be found here.

Some changes to the Travis build should also be made so that it can use this data for building.

From there on, the details submitted by them will be converted by a json object (using javascript) and further send to the open event server via a POST request where it will be written to a database.

We will be able to fetch this file from the database by the following link

openevent.com/api/v2/customapps/id.

Simultaneously one Travis build will also be trigger using the API that will auto build the latest commit, taking the modified json file data provided by the orga-server.

This configuration will be provided to Travis while the build time.

Cool, any difficulties yet!

One of the main challenges that we are facing is manually triggering the Travis build.

We can do this via the Travis API but that’s still in beta and also we are getting our head around on how to implement it.

I also had a tough time learning javascript and HTML for making the Web page and then I also have to read up on sending a POST request to the server via Ajax.

It’s a bit tough, but should be fun.

So, that was all for now, see you next week and all the best for your projects.✌

Continue Reading
Close Menu