public long start(String filename, InputStream in, Model modelin) {
		long time=-1;
		// Cleanup if thread already exists
		if (gcodepainter != null) {
			errormsg = null;
			setCmd(Commands.EXIT); // Stop thread
			if(pause != 0) togglePause();
			try {
				gcodepainter.join(10000);
				gcodepainter.interrupt();
			} catch (InterruptedException e) {
			}
			setCmd(Commands.NOOP);
			layers = null;
			model = null;
			g2.repaint();
		}
		System.gc();
		gcodepainter = new Thread(this);
		gcodepainter.start();
		extrazoom=1f;
		boolean ret;
		if (modelin == null) {
			try {
				model = new Model(filename);
				ret = false;
				if (in == null) {
					ret = model.loadModel();
				} else {
					ret = model.loadModel(in,in.available());
				}
			} catch (Exception e) {
				e.printStackTrace();
				errormsg = "Failed to load model. Is this a valid gcode file ?\n" + e.getMessage();
				g2.repaint();
				return time;
			}

			if (!ret) {
				errormsg = "Failed to load model.Check errors on command line.";
				g2.repaint();
				return time;
			}
			time = System.currentTimeMillis();
			model.analyze();
			time=(System.currentTimeMillis()-time);
			System.out.println("Load Model Analyse finished in ms:"+time);
		} else {
			model = modelin;
		}
		//overwrite manual extruder offset if defined by m218
		if(model.getExtruderOffset() != null){
			//extruderOffset = model.getExtruderOffset();
			//if m218 is used the offset in the gcode file is usually zero
			applyOffset=false;
		}
		layers = new ArrayList<Layer>(model.getLayer());
		return time;
	}