Tag: java

  • TabWidget demo project

    Sorry it took little longer than expected, run in some issues with cupcake (SDK 1.5)
    I have attached a Demo project for all interested with  some screenshots and modified .project for TabWidget Project(fixes cupcake problem ref http://groups.google.com/group/android-developers/browse_thread/thread/5537ae10e4143240) if you use eclipse.

    1. My env:
    Eclipse Version: 3.4.2
    Android SDK 1.5
    Windows

    2.After you import the TabWidgedDemo project you will probably need to fix your buildpath.
    Make sure to add TabWidet as a reference to TabWidgedDemo.

    3.In TabWidged project you will need to update the .project file otherwise you will get Verify error when deploying to the device.

    If you have any questions let me know, I hope you enjoy the project, more improvements to come

    Download tabwidgetdemo for eclipse

  • Serving resources using Resource PhaseListener

    PhaseListener designed to serve resources like css, javascript, images, pdf etc.. from jar file

    ResourcePhaseListener.java

    All required files can be downloaded here.

    package com.gregbugaj.jsfdump.console;
    
    import java.io.IOException;
    import java.io.InputStream;
    import java.util.HashMap;
    import java.util.Map;
    
    import javax.activation.MimetypesFileTypeMap;
    import javax.faces.context.FacesContext;
    import javax.faces.event.PhaseEvent;
    import javax.faces.event.PhaseId;
    import javax.faces.event.PhaseListener;
    import javax.servlet.ServletOutputStream;
    import javax.servlet.http.HttpServletResponse;
    
    import org.w3c.dom.Document;
    import org.w3c.dom.Node;
    import org.w3c.dom.NodeList;
    
    import com.gregbugaj.jsfdump.util.JarUtil;
    import com.gregbugaj.jsfdump.util.XMLUtil;
    /**
     * Serve resources from jar file  back to the user by specifying resource name in resource-config.xml
     * 
     * This works with following syntax if faces servlet is *.jsf  /jsfdump/resource/script.js.jsf
     * or  /jsfdump/resource/script.js if faces servlet is *.*
     * 
     * @author devil
     *
     */
    @SuppressWarnings("serial")
    public class ResourcePhaseListener implements PhaseListener {
    	//This is how the resource will be accessed ex /jsfdump/resource/script.js
    	private static final String RESOURCE_PREFIX = "/jsfdump/resource/";
    	//Location of where the js, img, css etc files reside inside the jar, we could also placed them in META-INF folder
    	private static final String RESOURCE_PATH = "/com/gregbugaj/jsfdump/resources/";
    	
    	private static Map resources=new HashMap();
    	private boolean isLoaded;
    
    	@Override
    	public void afterPhase(PhaseEvent event) {
    		FacesContext facesContext=event.getFacesContext();
    		String rootId=facesContext.getViewRoot().getViewId();
    		//Clean up key
    		String key=rootId.replace(RESOURCE_PREFIX, "");
    		key=key.replace(".xhtml", "");
    		key=key.replace(".jsf", "");
    		if(!rootId.startsWith(RESOURCE_PREFIX)){
    			return; 
    		}
    		
    		//Lazy loading
    		if(!isLoaded){
    			isLoaded=initResources();
    		}	
    		String resourceName=resources.get(key);
    		//Location of resources inside the jar file
    		String fileName=RESOURCE_PATH+resourceName;
    		InputStream resourceStream=JarUtil.getStreamFromJar(fileName);
    		HttpServletResponse response = (HttpServletResponse) facesContext.getExternalContext().getResponse();
    		response.setCharacterEncoding("UTF-8");
    		ServletOutputStream sos = null;
    		try {
    			sos = response.getOutputStream();
    			if(resourceStream!=null){
    				response.setStatus(HttpServletResponse.SC_OK);
    				//Resolve mime type, required that we have activation.jar loaded
    				//Additional mime types can be defined in /META-INF/mimes.types  {@link http://java.sun.com/j2ee/sdk_1.3/techdocs/api/javax/activation/MimetypesFileTypeMap.html }
    				String contentType = new MimetypesFileTypeMap().getContentType(fileName);
    				response.setContentType(contentType);
    				byte[] buffer= new byte[1024];
    				for (int bytesRead = 0; (bytesRead = resourceStream.read(buffer, 0, buffer.length)) > 0;)
    				{
    					sos.write(buffer, 0, bytesRead);
    				}
    			}else{
    				//Resource not found
    				response.setStatus(HttpServletResponse.SC_NOT_FOUND);
    				response.setContentType("text/html");
    			}
    			sos.flush();
    			sos.close();
    		} catch (IOException e) {
    			e.printStackTrace();
    		}
    		facesContext.responseComplete();
    	}
    
    	@Override
    	public void beforePhase(PhaseEvent event) {
    		//Do nothing
    	}
    
    	/**
    	 * Load resource mapping from resource-config.xml
    	 * @return true if we successfully loded resource
    	 */
    	private boolean initResources() {
    		boolean retVal=true;
    		InputStream stream=null;	
    		try {
    			stream=JarUtil.getStreamFromJar("/META-INF/resource-config.xml");
    			Document document=XMLUtil.getXmlDocument(stream);
    			NodeList resourceNodes=XMLUtil.extract("/resources/resource", document);
    			for(int i=0;i
    

    resource-config.xml

    This is where we define resources that we will be serving. One reasons we use xml configuration is to prevent security breaches.

      
      
    	
    	
    	
      
    

    Two common ways to access the resources are
    If faces servlet is *.jsf /jsfdump/resource/script.js.jsf
    Of /jsfdump/resource/script.js if faces servlet is *.*

    META-INF/mime.types

    This is where we add additional mime types, requires that we have activation.jar loaded More info

    This file is not required but it helps, for example png files resolve to application/octet-stream rather than image/x-png

    Examples

  • Specifying java source and target version in Maven 2

    While converting from Ant to Maven2 i have came across following error while trying to compile the project

    generics are not supported in -source 1.4
    (try -source 1.5 to enable generics)
    private Map  variables;
    

    To fix the problem we need to add the pluggin configuration to our pom.xml

    
    ...
        
            
                
                    org.apache.maven.plugins
                    maven-compiler-plugin
                    
                        1.5
                        1.5
                    
                
            
        
    ...
    
    

    Thats it.

  • Detecting Network Speed and Type on Android (Edge,3G)

    For better experience for users of my app I wanted to show them different UI based on their network speed, problem here is that there is no way to know what network we are currently on.

    My first instinct was to use android.net.ConnectivityManager getActiveNetworkInfo() which gives us current network information, but the only thing we can find out from this is the connection type TYPE_MOBILE or TYPE_WIFI which is not very useful for my purpose.

    So here is a quick tool that will try to determine network type by testing the download speed, I use threshold of 176 kbits/sec as EDGE cut of value.

    Downloads

    Screenshots

  • Carme GPS Tracker for Android

    My frist Android app, this is simple GPS tracker program that let us record our tracks, store  and share them.

    This project uses my custom TabWidget for Android.

    Main features

    • Record
    • Playback
    • Share via Email (Google Earth)
    • Share via Twitter  (in progress)
    • Exporting to SD Card
    • Tagging (in progress)

    I use icon from http://www.dryicons.com , love their methodology give the little guys an edge by providing free high quality designs.

    Screenshots

    [nggallery id=2]

    To Come

    Here are some other features that I will implement soon

    • Altitude profiler
    • Photos
    • Profiles

    Download Carme source code

  • Custom Android Tabs

    Due to limitation of Android Tab component I created a custom TabWidget that I am using in couple different projects already. The widget allows us to  add custom background and use custom icons, tabs   can be Top/Bottom aligned.

    Currently tabs can launch new Activity and  Dialog , when starting new Activity we can use  “startActivityForResult” so our tab will get a notification when other activity have finished.

    (more…)