Mittwoch, 30. April 2014

[Review] Recording the Screen or just a single window using Screencastify

As part of a project  I did at the university I needed to record a single window of my screen to a video. I searched google and even made it to page 5 (I am not kidding!!!). Finally I found a tool which worked really well for my tasks.

The tool I am talking about is called Screencastify and is a Google Chrome plugin. You now may ask yourselfs "What? A Chrome plugin?". I asked myself the same question but Screencastify is fantastic. You just download it via the Chrome plugin store using this link. Just download it and start the plugin. Now a tiny window will open on the top right corner.


You can choose between recording a single tab or the desktop. Using the desktop recording will create another popup in which you can choose which window the plugin should record. Just select the window you want to record and Screencastify does the rest of the work.

This was just a short post but I thought Screencastify deserves this one :)

Cheers,
Loris

Montag, 21. April 2014

[Web Development] The ways of animating stuff using JavaScript, JQuery and CSS

Because a co-worker asked me how to fade something in and out I thought about making a short overview on the techniques you can use to achieve animations. I will present you 3 ways how you could fade elements in and out.

The Plain JavaScript Way

DON'T DO IT. I tried this once. Took me about 8 hours to create kind of a translate animation but it still wasn't very smooth. Better use one of the two ways following.

The JQuery Way

After I did a JavaScript animation not knowing of JQuery, I have seen that you can create animations in JQuery within a single line.
$("div").fadeIn();
$("div").fadeOut();
$("div").fadeToggle();
JQuery even comes with a fadeToggle() method which will fade the element in if it is hidden at the moment and fade the element out if its visible.
Each of the presented methods have callbacks you can use like this
$("div").fadeIn("slow", function() {
    // Animation complete
});
Another way to achieve fading in JQuery is the following one but I don't really know why you should use this one.
//Will fade out the div in 5 seconds
$("div").animate({
    opacity: 0,
}, 5000, function() {
    //Will be executed after the animation
});

//Will fade in the div in 5 seconds
$("div").animate({
    opacity: 1,
}, 5000, function() {
    //Will be executed after the animation
});
To come to an end I present you my favorite way.

The CSS Way

CSS3 comes with the so called transitions. Each browser supporting CSS3 supports these animations. They are easy to implement and don't enlarge your JavaScript code. You can use it like this.
-webkit-transition: opacity 500ms ease-out 1s;
-moz-transition: opacity 500ms ease-out 1s;
-o-transition: opacity 500ms ease-out 1s;
transition: opacity 500ms ease-out 1s;
Now every change in the opacity of the element is animated. You just need to adjust the opacity using a single JQuery line like this
$("div").css("opacity", 0);
And all the magic is done now. Let me know your thinkings of the 3 ways and what are you using.
Have a good day :)

Sonntag, 20. April 2014

[Web Development] An overall tutorial in web development at the example of a gallery

First I would like to mention that I never learned web development professionally. I have taught everything concerning web development myself by creating a website for my brother who is a model (Lukas Bachert). So if you have any best-practices or improvements please let me know. Have fun :)

What we are going to do:

We are going to create a fancy image gallery as seen on my website. We will achieve this step by step while I am trying to explain a lot so you can do similar projects after you finished this tutorial.

What you should know to follow this tutorial:

I am trying to make this tutorial as easy as possible but you should know the following things in order to follow and understand the tutorial:

  • The basics of HTML including the types of elements and their usages
  • The basics of CSS including simple selection (If you are lacking skills in selecting elements in CSS check out this link)
  • You should know what JQuery is


The structure:

black:   the div containing our gallery
blue:     the div our content will be
green:   the arrows to navigate through the images
red:      the div containing the thumbs
orange: the arrows to scroll through the thumbs

The HTML:

As a start we will implement the mentioned structure as HTML code.
<!-- This is our all aroung container -->
<div id="epicGallery">
 <!-- This will contain our thumbs -->
 <div id="epicThumbs">
 </div>
 <!-- The following two are for scrolling the thumbs -->
 <div class="epic-thumb-nav" id="epicThumbsLeft">
 </div>
 <div class="epic-thumb-nav" id="epicThumbsRight">
 </div>
 <!-- This will contain our content -->
 <div id="epicContent">
  <!-- This is the big image -->
  <img id="epicImage" src=""/>
  <!-- The following divs are for navigating through the images -->
  <div class="epic-nav" id="epicNext">
  </div>
  <div class="epic-nav" id="epicPrevious">
  </div>
 </div>
</div>
Because I take the source code of the plugin I published the ids are structured like that. I started naming ids in camel-case and classes seperated by "-". Do you guys have any best-practices for that?

Now we got some empty divs. Time to fill them:
 <div id="epicGallery">
 <!-- This will contain our thumbs -->
 <div id="epicThumbs">
 </div>
 <!-- The following two are for scrolling the thumbs -->
 <div class="epic-thumb-nav" id="epicThumbsLeft">
  <!-- Left Arrow to scroll the thumbs-->
  <img class="epic-thumb-nav-image" src="LeftBlackArrow.png" alt=""/>
 </div>
 <div class="epic-thumb-nav" id="epicThumbsRight">
  <!-- Right Arrow to scroll the thumbs-->
  <img class="epic-thumb-nav-image" src="RightBlackArrow.png" alt=""/>
 </div>
 <!-- This will contain our content -->
 <div id="epicContent">
  <!-- This is the big image -->
  <img id="epicImage" src="" onclick="epicPopup();" alt=""/>
  <!-- The following divs are for navigation -->
  <div class="epic-nav" id="epicNext">
   <!-- Right Arrow to show the next image -->
   <img class="epic-nav-image" src="RightBlackArrow.png" onclick="epicNext();" alt=""/>
  </div>
  <div class="epic-nav" id="epicPrevious">
   <!-- Left Arrow to show the previous image -->
   <img class="epic-nav-image" src="LeftBlackArrow.png" onclick="epicPrevious();" alt=""/>
  </div>
 </div>
</div>
I hope you could follow so far. Now we just need to add a little magic until we are finished. You need to place a span in front of each image to vertically align it. Thanks to Steve Clay solving the problem in this post. If you do that you finally get this code:
<!-- This is our all aroung container -->
<div id="epicGallery">
 <!-- This will contain our thumbs -->
 <div id="epicThumbs">
 </div>
 <!-- The following two are for scrolling the thumbs -->
 <div class="epic-thumb-nav" id="epicThumbsLeft">
  <!-- Left Arrow to scroll the thumbs-->
  <span class="epic-helper"><img class="epic-thumb-nav-image" src="LeftBlackArrow.png" alt=""/>
 </div>
 <div class="epic-thumb-nav" id="epicThumbsRight">
  <!-- Right Arrow to scroll the thumbs-->
  <span class="epic-helper"><img class="epic-thumb-nav-image" src="RightBlackArrow.png" alt=""/>
 </div>
 <!-- This will contain our content -->
 <div id="epicContent">
  <!-- This is the big image -->
  <span class="epic-helper"><img id="epicImage" src="" onclick="epicPopup();" alt=""/>
  <!-- The following divs are for navigation -->
  <div class="epic-nav" id="epicNext">
   <!-- Right Arrow to show the next image -->
   <span class="epic-helper"><img class="epic-nav-image" src="RightBlackArrow.png" onclick="epicNext();" alt=""/>
  </div>
  <div class="epic-nav" id="epicPrevious">
   <!-- Left Arrow to show the previous image -->
   <span class="epic-helper"><img class="epic-nav-image" src="LeftBlackArrow.png" onclick="epicPrevious();" alt=""/>
  </div>
 </div>
</div>
Because the four arrows we see now if we are executing out website are not really what we want we need to add some CSS to make it at least good looking.

The CSS: We start by some general CSS lines we need.
//Our main container
#epicGallery {
    position: absolute;
    width: 80%;
    height: 80%;
    top: 10%;
    left: 10%;
    overflow: hidden;
}

//This is the span that helps to align images vertically
.epic-helper {
    display: inline-block;
    height: 100%;
    vertical-align: middle;
}
The .epic-helper is the span i talked about earlier. It is needed to align the images.
Let's go on by styling the thumbs.
//The thumb container
#epicThumbs {
    position: absolute;
    left: 0px;
    min-width: 100%; //Needs to be at least 100%. If it's larger you can scroll it
    bottom: 0px;
    max-height: 80px;
    height: 80px;
    overflow: hidden;
    white-space: nowrap;
    //Animate the scrolling
    transition: left 0.2s linear;
    -moz-transition: left 0.2s linear;
    -o-transition: left 0.2s linear;
    -webkit-transition: left 0.2s linear;
}

.epic-thumb {
    display: inline-block; //Prevent the wrap of divs
    height: 100%;
    margin-left: 5px; //A little gap between the thumbs
    cursor: pointer;
}
To finish the thumbs we need to define the arrows which we will use to scroll the thumbs later. I guess I need to mention now that every animation in our gallery will be a CSS transition. I really love these animations. They look smooth and are compatible to common browsers.
.epic-thumb-nav {
    position: absolute;
    width: 50px;
    height: 80px;
    bottom: 0px;
    //Make it a transparent white background
    background-color: rgba(255,255,255,0.4);
    //opacity will be set if you hover the thumbs
    opacity: 0;
    //Animate the opacity so it looks a lot better
    transition: opacity 0.5s ease-in-out;
    -moz-transition: opacity 0.5s ease-in-out;
    -o-transition: opacity 0.5s ease-in-out;
    -webkit-transition: opacity 0.5s ease-in-out;
}

#epicThumbsRight {
    right: 0px;
}

//The animation I mentioned. Fading in/out the arrows of the thumbs
#epicThumbs:hover ~ .epic-thumb-nav {
    opacity: 1;
}

.epic-thumb-nav:hover {
    opacity: 1;
}

//Vertically align the image
.epic-thumb-nav-image {
    vertical-align: middle;
    width: 100%;
}
Now that we finished our thumbs we can start with the content. First of all we will do the general stuff and after that we will style the arrows in the content.
#epicContent {
    text-align: center;
    width: 100%;
    height: calc(100% - 90px);
    max-width: 100%;
    max-height: calc(100% - 90px);
}

#epicImage {
    max-width: 100%;
    max-height: 100%;
    vertical-align: middle;
    cursor: pointer;
}

/* ----------------------------------------------------------------------------- CONTENT-NAV */

//Fade in the content arrows if you hover the content
#epicContent:hover > .epic-nav {
    opacity: 1;
}

.epic-nav {
    position: absolute;
    top: 0px;
    height: calc(100% - 90px);
    width: 50px;
    //Initially the arrows aren't visible
    opacity: 0;
    //Animate the opacity so it looks smooth
    transition: opacity 0.5s ease-in-out;
    -moz-transition: opacity 0.5s ease-in-out;
    -o-transition: opacity 0.5s ease-in-out;
    -webkit-transition: opacity 0.5s ease-in-out;
}

//Position both arrows
#epicNext {
    right: 0px;
}

#epicPrevious {
    left: 0px;
}

//Vertically align the images
.epic-nav-image {
    vertical-align: middle;
    width: 100%;
    cursor: pointer;
}
Finally we will style something we didn't even implement in our HTML. If you are asking yourself why we should do such a thing you are right. That sounds really stupid. But the answer is easy. Later on we want a pretty popup which extends the current image. The popup will be loaded by a template we will create at the end of the tutorial.
//A black transparent background
#epicBackground {
    position: absolute;
    width: 100%;
    height: 100%;
    top: 0px;
    left: 0px;
    background-color: rgba(0,0,0,0.7);
}

//The content of the popup including the image and the navigation arrows
#epicFullscreenContainer {
    position: absolute;
    text-align: center;
    width: 90%;
    height: 90%;
    max-width: 90%;
    max-height: 90%;
    top: 5%;
    left: 5%;
}

#epicFullscreenImage {
    max-width: 100%;
    max-height: 100%;
    vertical-align: middle;
}

/* ----------------------------------------------------------------------------- POPUP-NAV */

.epic-popup-nav {
    position: absolute;
    top: 5%;
    height: 90%;
    width: 50px;
}

#epicPopupNext {
    left: 95%;
}

#epicPopupPrevious {
    left: calc(5% - 50px);
}
Well done, you finished the CSS part. I hope you understood everything. If you had any troubles or some things you don't understand please let me know :)
Just one step left to our final gallery. We will now start using JavaScript and JQuery.

The JavaScript/JQuery:

Good job so far. Let's start the JavaScript and JQuery part by initializing the variables and set up the eventhandlers.
//Out current image index
var epicIndex = -1;
//Is needed for better detection by scrolling the thumbs
var isHover = false;

$(document).ready(function() {
    setUpEventHandler();
});
Now to the core of our JavaScript file, the setUpEventHandler() method.
//sets up the needed handler
function setUpEventHandler() {
 //Executes when an thumb image is clicked
    $('.epic-thumb').click(function() {
  //Check if clicked element is current element
        if ($('#epicThumbs').children().index($(this)) !== epicIndex) {
   //Update the image and the current index
            var src = $(this).attr('src');
            $('#epicImage').attr('src', src);
            $('#epicFullscreenImage').attr('src', src);
            epicIndex = $('#epicThumbs').children().index($(this));
        }
    });
 //that unbind is needed so if you execute this method twice the following method
 //won't be executed twice
    $(document).unbind('keyup');
 //This method is used so you can navigate the gallery with the arrow keys on your keyboard
    $(document).keyup(function(e) {
        if (e.keyCode === 37) { //LEFT-ARROW
            epicPrevious();
        } else if (e.keyCode === 39) { //RIGHT-ARROW
            epicNext();
        } else if (e.keyCode === 27) { //ESCAPE
   //If the popup is shown it will be faded out
            $('#epicBackground').fadeOut(200, function() {
                $('#epicBackground').remove();
                $('#epicGallery').fadeIn('fast');
            });
        }
    });
 //This method is needed so the thumb arrows are hidden or shown at the correct times
 //E.g. if you scrolled the whole thumbs to the end you should not see the arrow to scroll further
    $('#epicThumbs').mouseenter(function() {
        if ($('#epicThumbs').width() > $('#epicGallery').width()) {
            var left = parseInt($('#epicThumbs').css('left'));
            if (left < 0) {
                $('#epicThumbsLeft').show();
            }
   //Again some mathematical calculations...
            var divWidth = $('#epicGallery').width();
            var thumbWidth = $('#epicThumbs').width();
            var maxLeft = -(thumbWidth - divWidth);
            var left = parseInt($('#epicThumbs').css('left'));
            if (left > maxLeft) {
                $('#epicThumbsRight').show();
            }
        } else {
            $('#epicThumbsLeft').hide();
            $('#epicThumbsRight').hide();
        }
    });
    $('#epicThumbsRight').mouseenter(function() {
        isHover = true;
        moveThumbsLeft();
    });
    $('#epicThumbsRight').mouseleave(function() {
        isHover = false;
    });
    $('#epicThumbsLeft').mouseenter(function() {
        isHover = true;
        moveThumbsRight();
    });
    $('#epicThumbsLeft').mouseleave(function() {
        isHover = false;
    });
    $('#epicThumbs').children().first().click();
}
That was a hell of a lot of code. I hope there are no difficulties in it and the comments i made are clear.
Now we need to be able to navigate through the images in our gallery. We will implement the methods epicNext() and epicPrevious().
//Updates the image to the next image in the gallery.
//If you reached the end the gallery starts all over again.
function epicNext() {
    epicIndex++;
    if (epicIndex > $('#epicThumbs').children().size() - 1) {
        epicIndex = 0;
    }
    var next = $('#epicThumbs').children().get(epicIndex);
    var nextSrc = $(next).attr('src');
    $('#epicImage').attr('src', nextSrc);
    $('#epicFullscreenImage').attr('src', nextSrc);
}

//Updates the image to the previous image in the gallery.
//If you reached the end the gallery starts all over again.
function epicPrevious() {
    epicIndex--;
    if (epicIndex < 0) {
        epicIndex = $('#epicThumbs').children().size() - 1;
    }
    var next = $('#epicThumbs').children().get(epicIndex);
    var nextSrc = $(next).attr('src');
    $('#epicImage').attr('src', nextSrc);
    $('#epicFullscreenImage').attr('src', nextSrc);
}
Only three methods left. Two for the scrolling of the thumbs and one for the popup.
//moves the thumbs left
function moveThumbsLeft() {
 //some mathematical calculations
    var divWidth = $('#epicGallery').width();
    var thumbWidth = $('#epicThumbs').width();
    var maxLeft = -(thumbWidth - divWidth);
    var left = parseInt($('#epicThumbs').css('left'));
    $('#epicThumbsLeft').show();
 //If the thumbs reached its final position where it shouldnt move further the 
 //arrow to scroll further is hidden
    if (left <= maxLeft) {
        $('#epicThumbs').css('left', maxLeft);
        $('#epicThumbsRight').hide();
    } else if (isHover) {
        $('#epicThumbs').css('left', "-=75");
        if ($('#epicThumbs').width() > $('#epicGallery').width()) {
            $('#epicThumbsRight').show();
        }
        setTimeout(moveThumbsLeft, 200);
    }
}

//moves the thumbs right
function moveThumbsRight() {
    var left = parseInt($('#epicThumbs').css('left'));
    $('#epicThumbsRight').show();
 //If the thumbs reached its final position where it shouldnt move further the 
 //arrow to scroll further is hidden
    if (left >= 0) {
        $('#epicThumbs').css('left', 0);
        $('#epicThumbsLeft').hide();
    } else if (isHover) {
        $('#epicThumbs').css('left', "+=75");
        if ($('#epicThumbs').width() > $('#epicGallery').width()) {
            $('#epicThumbsLeft').show();
        }
        setTimeout(moveThumbsRight, 200);
    }
}
The code for the popup
//This method is used to create the popup we want to happen if we click the image.
function epicPopup() {
 //fades out the gallery so that you dont see the gallery in the background of the popup
    $('#epicGallery').fadeOut('fast');
 //create a div
    jQuery('
', { id: 'epicBackground' }).appendTo('body'); $('#epicBackground').hide(); //Load the template into the div $('#epicBackground').load('epicPopup.html', function() { $('#epicFullscreenImage').attr('src', $('#epicImage').attr('src')); }); //Fade the popup in $('#epicBackground').fadeIn(200); //Close the popup if the background is clicked $('#epicBackground').click(function(e) { var noclose = (e.target === document.getElementById('epicFullscreenImage')) || (e.target === document.getElementById('epicPopupPreviousImage')) || (e.target === document.getElementById('epicPopupNextImage')); //Be sure that the background is clicked and not any children of the background if (noclose) { return false; } else { $('#epicBackground').fadeOut(200, function() { $('#epicBackground').remove(); $('#epicGallery').fadeIn('fast'); }); } }); }
We did it. We finally did it. Well... Not really. We are missing a short piece of HTML. You remember that template for the popup i talked about earlier? Here it is:

<div id="epicFullscreenContainer">
    <span class="epic-helper"></span><img id="epicFullscreenImage" src="" alt=""/>
</div>
<!-- The same navigation as every year
  and some helping spans aswell -->
<div class="epic-popup-nav" id="epicPopupNext">
    <span class="epic-helper"></span><img id="epicPopupNextImage" class="epic-nav-image" src="images/epicgallery/right_black.png" onclick="epicNext();" alt=""/>
</div>
<div class="epic-popup-nav" id="epicPopupPrevious">
    <span class="epic-helper"></span><img id="epicPopupPreviousImage" class="epic-nav-image" src="images/epicgallery/left_black.png" onclick="epicPrevious();" alt=""/>
</div>
Finally. That is all the magic needed to develop a gallery like I did. Now you can add images to your gallery by inserting lines like this one in your epicThumbs container

<img class="epic-thumb" src="some/path/11.jpg" alt="this could be your advertisement"/>

I hope you had fun and understood what I did. If you liked this post please recommend it to some other people. Have a nice day! :)

Freitag, 11. April 2014

[Review] Vuzix M100 - not yet



Today I am talking about the Vuzix M100 I mentioned in the post before. The Vuzix M100 is an alternative to the Google Glasses everyone is talking about. I never seen a Google Glass before but I hope they did a better job than Vuzix did at their M100.

Screen

The device comes with a 428 x 240 px screen. This does not sound much but in my opinion this is enough because the screen is really close to your eye.

Battery

Vuzix anounces that the integrated battery lasts up to 8 hours. I tested this by just leaving the device on over night. After 8 hours I checked if it is still running and I was surprised that the battery just dropped to 20%. Good job, Vuzix.

Sound

Alhough the speaker is really near to your ear it is really, really quiet even at max volume. You can also listening music using your Vuzix M100 but to be honest, you really do not want to. The sound is terrible.

Camera

After that negative statement I have to credit Vuzix for the integrated 720p HD Camera. You can walk around filming everyone in your way in a really good quality. A red LED on the device informs everyone seeing the device that you are filming.

Mounting the device

Simply you can not mount the device in a comfortable way if you want to see the screen. There is a clip which you can use to wear the device directly on your head. About 10 minutes later you really need to take the device off because your ears and your head is hurting. Vuzix also delivers kind of protective goggles known from chemistry. You look like an idiot wearing them but they are comfortable and you can see the screen.

Using the device

Using the device is not easy. This is because the device does not have a voice control yet. Vuzix anounced a voice control later on but for now you always need your smartphone (and the Vuzix app) to use your M100. This is really annoying and the device is not worth its money. I hope Vuzix will publish an update fast.

Developing

Because the Vuzix M100 is an android device you can develop for it like for each other android device. Vuzix is delivering a SDK but do not celebtrate just yet. The SDK contains just installation PDFs and an emulator like each other android emulater. No API or something :(

Conclusion

If you are thinking about buying the Vuzix M100 you simply should not yet. It is still in its infancy and not useful like that. Just wait how the market develops and keep an eye on the Google Glasses.

EDIT

Vuzix published a new OS for the M100. They are talking about a voice control and gesture control aswell. I look foreward to test it. I hope that Vuzix did a good job with this OS.


Mittwoch, 9. April 2014

[Android] Continous Speech Recognition

This is a tutorial for implementing a continous speech recognition in Android. I am writing this because I had a lot of trouble myself developing it.

What you should know
  • The basics of Java including interfaces and inheritance
  • The basics of Android development
Preface

I got a lecture called "Software Engineering" in which all students need to develop applications for wearable devices. We got a pretty cool idea which application we want to create but I can not describe it yet because we are not sure about publishing the application. Our application should run on Smartphones with Android 4.0.4 or higher (just the speech recognition does not need such a high api level) and on Smart Glasses aswell. For this reason my university ordered a device called Vuzix M100. I am going to make an extra post about the impressions I got using this device.

Motivation

Imagine this scenario:
You are leaving the grovery store, having your pretty cool Smart Glasses on. Problem is you want to interact with the device but you can not because on each finger you carry a bag full of let's say beer. What to do now? The answer ist continuos speech recognition, meaning a speech recognition service running all the time so you do not have to press any button or touch the device. You simply say "Call my wife" and the Smart Glasses directly conects to the smartphone and call her. Motivated enough?

And now to the actual topic

The implementation we are about to use will contain 3 classes. The VoiceRecognitionListener and the ListeningActivity which implements the interface IVoiceControl. The ListeningActivity includes the main functionalities we will use but we will create our IVoiceControl and the VoiceRecognitionListener first. 

The VoiceRecognitionListener holds a list of IVoiceControl and informs all IVoiceControl that a speech command has been found.
package de.lorisbachert.continousspeechrecognizer;

/**
 * Created by Loris on 26.02.14.
 */
public interface IVoiceControl {
    public abstract void processVoiceCommands(String... voiceCommands); // This will be executed when a voice command was found
    
    public void restartListeningService(); // This will be executed after a voice command was processed to keep the recognition service activated
}
The VoiceRecognitionListener contains the following code:
package de.lorisbachert.continousspeechrecognizer;

import java.util.ArrayList;

import android.os.Bundle;
import android.speech.RecognitionListener;
import android.speech.SpeechRecognizer;

public class VoiceRecognitionListener implements RecognitionListener {
 
 private static VoiceRecognitionListener instance = null;
 
 IVoiceControl listener; // This is your running activity (we will initialize it later)
 
 public static VoiceRecognitionListener getInstance() {
  if (instance == null) {
   instance = new VoiceRecognitionListener();
  }
  return instance;
 }
 
 private VoiceRecognitionListener() { }
 
 public void setListener(IVoiceControl listener) {
        this.listener = listener;
    }
 
    public void processVoiceCommands(String... voiceCommands) {
        listener.processVoiceCommands(voiceCommands);
    }
 
    // This method will be executed when voice commands were found
 public void onResults(Bundle data) {
  ArrayList matches = data.getStringArrayList(SpeechRecognizer.RESULTS_RECOGNITION);
  String[] commands = new String[matches.size()];
  for (String command : matches) {
   System.out.println(command);
  }
  commands = matches.toArray(commands);
  processVoiceCommands(commands);
 }
 
 // User starts speaking
 public void onBeginningOfSpeech() {
  System.out.println("Starting to listen");
 }
 
 public void onBufferReceived(byte[] buffer) { }
 
 // User finished speaking
 public void onEndOfSpeech() {
  System.out.println("Waiting for result...");
 }
 
 // If the user said nothing the service will be restarted
 public void onError(int error) {
  if (listener != null) {
   listener.restartListeningService();
  }
 }
 public void onEvent(int eventType, Bundle params) { }
 
 public void onPartialResults(Bundle partialResults) { }
 
 public void onReadyForSpeech(Bundle params) { }
 
 public void onRmsChanged(float rmsdB) { }
}
Now that we implemented the VoiceRecognitionListener we will finish the service by implementing the ListeningActivity:
package de.lorisbachert.continousspeechrecognizer;

import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.speech.RecognizerIntent;
import android.speech.SpeechRecognizer;
import android.util.Log;
import android.widget.Toast;

public abstract class ListeningActivity extends Activity implements IVoiceControl {

 protected SpeechRecognizer sr;
 protected Context context;
 
 @Override
 protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
 }
 
 // starts the service
 protected void startListening() {
  try {
   initSpeech();
   Intent intent = new Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH);
   intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL,RecognizerIntent.LANGUAGE_MODEL_WEB_SEARCH);
   if (!intent.hasExtra(RecognizerIntent.EXTRA_CALLING_PACKAGE))
      {
    intent.putExtra(RecognizerIntent.EXTRA_CALLING_PACKAGE,
                  "com.dummy");
      }
   sr.startListening(intent);
  } catch(Exception ex) {
   Log.d("SpeechRecognitionService", "Bei der Initialisierung des SpeechRecognizers ist ein Fehler aufgetreten");
  }
 }
 
 // stops the service
 protected void stopListening() {
  if (sr != null) {
   sr.stopListening();
         sr.cancel();
         sr.destroy();
        }
  sr = null;
 }
 
 protected void initSpeech() {
  if (sr == null) {
   sr = SpeechRecognizer.createSpeechRecognizer(this);
   if (!SpeechRecognizer.isRecognitionAvailable(context)) {
    Toast.makeText(context, "Speech Recognition is not available",
      Toast.LENGTH_LONG).show();
    finish();
   }
   sr.setRecognitionListener(VoiceRecognitionListener.getInstance());
  }
 }
 
 @Override
 public void finish() {
  stopListening();
  super.finish();
 }
 
 @Override
 protected void onStop() {
  stopListening();
  super.onStop();
 }
 
    @Override
 protected void onDestroy() {
     if (sr != null) {
         sr.stopListening();
         sr.cancel();
         sr.destroy();
        }
     super.onDestroy();
    }
    
    @Override
    protected void onPause() {
        if(sr!=null){
            sr.stopListening();
            sr.cancel();
            sr.destroy();              

        }
        sr = null;

        super.onPause();
    }
    
    //is abstract so the inheriting classes need to implement it. Here you put your code which should be executed once a command was found
 @Override
 public abstract void processVoiceCommands(String ... voiceCommands);
    
 @Override
 public void restartListeningService() {
  stopListening();
  startListening();
 }
}

That is all the magic. Now we just add these two permissions in our AndroidManifest.xml: 

<uses-permission android:name="android.permission.RECORD_AUDIO" />
<uses-permission android:name="android.permission.INTERNET" />
To sum everything up I wrote a short example usage:
package de.lorisbachert.continousspeechrecognizer;

import android.graphics.Color;
import android.os.Bundle;
import android.view.Gravity;
import android.widget.LinearLayout;
import android.widget.TextView;

public class MainActivity extends ListeningActivity {

 private LinearLayout content;
 
 @Override
 protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  setContentView(R.layout.activity_main);
  
  content = (LinearLayout)findViewById(R.id.commands);
  
  // The following 3 lines are needed in every onCreate method of a ListeningActivity
  context = getApplicationContext(); // Needs to be set
  VoiceRecognitionListener.getInstance().setListener(this); // Here we set the current listener
  startListening(); // starts listening
 }

 // Here is where the magic happens
 @Override
 public void processVoiceCommands(String... voiceCommands) {
  content.removeAllViews();
  for (String command : voiceCommands) {
   TextView txt = new TextView(getApplicationContext());
   txt.setText(command);
   txt.setTextSize(20);
   txt.setTextColor(Color.BLACK);
   txt.setGravity(Gravity.CENTER);
   content.addView(txt);
  }
  restartListeningService();
 }
}
That is it. Now we can test our little speech recognizer and having fun by using it.
If you have any trouble following my tutorial or any suggestions please let me know in the comments :)

You can download a demo project which can be executed using this link.

Hi, I am Loris

In this post I am going to introduce myself a bit.
My name is Loris Bachert and I am an applied computer science student from Germany. Since english is not my mother tongue please forgive me some further failures.
I am 20 years old and looking foreward to get my bachelor of science. At the age of 13 I started developing some simple programs in Microsoft Excel using VBA. About one year later I started learning C#. At this time I was bored by the standard windows desktop and tried some desktop applications including a Playstation 3 like menu.

The Playstation 3 menu I made in C#

I know this one is not a pretty application but I just started developing at this time.

The most complex project I did using C# was a music file handler. I had a lot of untagged and unsorted music on my computer and some day I had a thinking like "Hey, how about an automated tagging and sorting program" so I started cowboycoding a lot. Due to my loss of experience I did not know anything about making a concept or planing software like I know now. Because of that the code I wrote was bloodcurdling. And it worked fine (at least most times :) ).
I began studying in 2012 by learning Java and JavaFX. In my leisure time I introduced myself to web development and design.
Today I prefer to do some web related stuff like updating my website or developing websites just to improve my knowledge. You can follow this link to check out my website including web-plugins and some design.

I hope you enjoy my tutorials and thoughts about technologies and languages.

For further details you might check the about page of my website.


What is this thing?

Is it a bird? Is it a plane? No, it is my blog.
I am going to present you some of the projects I have done and I am currently doing.
In this blog you will find screenshots and code snippets including technologies like
  • HTML
  • JavaScript
  • CSS
  • Java
  • and JavaFX
If you do not understand something or have some questions you can easily contact me via blog@loris-bachert.de.

To see some of my projects and live demos you can check my website:
www.loris-bachert.com