Beispiel #1
0
/**
 * Load a single JPG into a Trackwaypoint Layer as a waypoint
 *
 * @top:      The Aggregate layer that a new TRW layer may be created in
 * @filename: The JPG filename
 * @vvp:      The viewport
 *
 * Returns: Whether the loading was a success or not
 *
 * If the JPG has geotag information then the waypoint will be created with the appropriate position.
 *  Otherwise the waypoint will be positioned at the current screen center.
 * If a TRW layer is already selected the waypoint will be created in that layer.
 */
gboolean a_jpg_load_file ( VikAggregateLayer *top, const gchar *filename, VikViewport *vvp )
{
	gboolean auto_zoom = TRUE;
	VikWindow *vw = (VikWindow *)(VIK_GTK_WINDOW_FROM_LAYER(VIK_LAYER(top)));
	VikLayersPanel *vlp = vik_window_layers_panel ( vw );
	// Auto load into TrackWaypoint layer if one is selected
	VikLayer *vtl = vik_layers_panel_get_selected ( vlp );

	gboolean create_layer = FALSE;
	if ( vtl == NULL || vtl->type != VIK_LAYER_TRW ) {
		// Create layer if necessary
		vtl = vik_layer_create ( VIK_LAYER_TRW, vvp, FALSE );
		vik_layer_rename ( vtl, a_file_basename ( filename ) );
		create_layer = TRUE;
	}

	gchar *name = NULL;
	VikWaypoint *wp = NULL;
#ifdef VIK_CONFIG_GEOTAG
	wp = a_geotag_create_waypoint_from_file ( filename, vik_viewport_get_coord_mode (vvp), &name );
#endif
	if ( wp ) {
		// Create name if geotag method didn't return one
		if ( !name )
			name = g_strdup ( a_file_basename ( filename ) );
		vik_trw_layer_filein_add_waypoint ( VIK_TRW_LAYER(vtl), name, wp );
		g_free ( name );
	}
	else {
		wp = vik_waypoint_new ();
		wp->visible = TRUE;
		vik_trw_layer_filein_add_waypoint ( VIK_TRW_LAYER(vtl), (gchar*) a_file_basename(filename), wp );
		vik_waypoint_set_image ( wp, filename );
		// Simply set position to the current center
		wp->coord = *( vik_viewport_get_center ( vvp ) );
		auto_zoom = FALSE;
	}

	// Complete the setup
	vik_layer_post_read ( vtl, vvp, TRUE );
	if ( create_layer )
		vik_aggregate_layer_add_layer ( top, vtl, FALSE );
	if ( auto_zoom )
		vik_trw_layer_auto_set_view ( VIK_TRW_LAYER(vtl), vvp );

	// ATM This routine can't fail
	return TRUE;
}
Beispiel #2
0
/**
 * Process selected files and try to generate waypoints storing them in the given vtl
 */
static gboolean datasource_geotag_process ( VikTrwLayer *vtl, ProcessOptions *po, BabelStatusFunc status_cb, acq_dialog_widgets_t *adw, gpointer not_used )
{
	datasource_geotag_user_data_t *user_data = (datasource_geotag_user_data_t *)adw->user_data;

	// Process selected files
	// In prinicple this loading should be quite fast and so don't need to have any progress monitoring
	GSList *cur_file = user_data->filelist;
	while ( cur_file ) {
		gchar *filename = cur_file->data;
		gchar *name;
		VikWaypoint *wp = a_geotag_create_waypoint_from_file ( filename, vik_viewport_get_coord_mode ( adw->vvp ), &name );
		if ( wp ) {
			// Create name if geotag method didn't return one
			if ( !name )
				name = g_strdup ( a_file_basename ( filename ) );
			vik_trw_layer_filein_add_waypoint ( vtl, name, wp );
			g_free ( name );
		}
		else {
			gchar* msg = g_strdup_printf ( _("Unable to create waypoint from %s"), filename );
			vik_window_statusbar_update ( adw->vw, msg, VIK_STATUSBAR_INFO );
			g_free (msg);
		}
		g_free ( filename );
		cur_file = g_slist_next ( cur_file );
	}

	/* Free memory */
	g_slist_free ( user_data->filelist );

	// No failure
	return TRUE;
}
Beispiel #3
0
/* example: 
     gboolean is_gpx = a_file_check_ext ( "a/b/c.gpx", ".gpx" );
*/
gboolean a_file_check_ext ( const gchar *filename, const gchar *fileext )
{
  g_return_val_if_fail ( filename != NULL, FALSE );
  g_return_val_if_fail ( fileext && fileext[0]=='.', FALSE );
  const gchar *basename = a_file_basename(filename);
  if (!basename)
    return FALSE;

  const char * dot = strrchr(basename, '.');
  if (dot && !strcmp(dot, fileext))
    return TRUE;

  return FALSE;
}
Beispiel #4
0
VikDEM *vik_dem_new_from_file(const gchar *file)
{
  FILE *f=NULL;
  VikDEM *rv;
  gchar buffer[DEM_BLOCK_SIZE+1];

  /* use to record state for dem_parse_block */
  gint cur_column = -1;
  gint cur_row = -1;
  const gchar *basename = a_file_basename(file);

  if ( g_access ( file, R_OK ) != 0 )
    return NULL;

  if ( (strlen(basename)==11 || ((strlen(basename) == 15) && (basename[11] == '.' && basename[12] == 'z' && basename[13] == 'i' && basename[14] == 'p'))) &&
       basename[7]=='.' && basename[8]=='h' && basename[9]=='g' && basename[10]=='t' &&
       (basename[0] == 'N' || basename[0] == 'S') && (basename[3] == 'E' || basename[3] =='W')) {
    gboolean is_zip_file = (strlen(basename) == 15);
    rv = vik_dem_read_srtm_hgt(file, basename, is_zip_file);
    return(rv);
  }

      /* Create Structure */
  rv = g_malloc(sizeof(VikDEM));

      /* Header */
  f = g_fopen(file, "r");
  if ( !f ) {
    g_free ( rv );
    return NULL;
  }
  buffer[fread(buffer, 1, DEM_BLOCK_SIZE, f)] = '\0';
  if ( ! dem_parse_header ( buffer, rv ) ) {
    g_free ( rv );
    return NULL;
  }
  /* TODO: actually use header -- i.e. GET # OF COLUMNS EXPECTED */

  rv->columns = g_ptr_array_new();
  rv->n_columns = 0;

      /* Column -- Data */
  while (! feof(f) ) {
     gchar *tmp;

     /* read block */
     buffer[fread(buffer, 1, DEM_BLOCK_SIZE, f)] = '\0';

     /* Fix Fortran-style exponentiation */
     tmp = buffer;
     while (*tmp) {
       if ( *tmp=='D')
         *tmp='E';
       tmp++;
     }

     dem_parse_block(buffer, rv, &cur_column, &cur_row);
  }

     /* TODO - class C records (right now says 'Invalid' and dies) */

  fclose(f);
  f = NULL;

  /* 24k scale */
  if ( rv->horiz_units == VIK_DEM_HORIZ_UTM_METERS && rv->n_columns >= 2 )
    rv->north_scale = rv->east_scale = GET_COLUMN(rv, 1)->east_west - GET_COLUMN(rv,0)->east_west;

  /* FIXME bug in 10m DEM's */
  if ( rv->horiz_units == VIK_DEM_HORIZ_UTM_METERS && rv->north_scale == 10 ) {
    rv->min_east -= 100;
    rv->min_north += 200;
  }


  return rv;
}
Beispiel #5
0
VikLoadType_t a_file_load ( VikAggregateLayer *top, VikViewport *vp, const gchar *filename_or_uri )
{
  g_return_val_if_fail ( vp != NULL, LOAD_TYPE_READ_FAILURE );

  char *filename = (char *)filename_or_uri;
  if (strncmp(filename, "file://", 7) == 0) {
    // Consider replacing this with:
    // filename = g_filename_from_uri ( entry, NULL, NULL );
    // Since this doesn't support URIs properly (i.e. will failure if is it has %20 characters in it)
    filename = filename + 7;
    g_debug ( "Loading file %s from URI %s", filename, filename_or_uri );
  }
  FILE *f = xfopen ( filename );

  if ( ! f )
    return LOAD_TYPE_READ_FAILURE;

  VikLoadType_t load_answer = LOAD_TYPE_OTHER_SUCCESS;

  gchar *dirpath = g_path_get_dirname ( filename );
  // Attempt loading the primary file type first - our internal .vik file:
  if ( check_magic ( f, VIK_MAGIC ) )
  {
    if ( file_read ( top, f, dirpath, vp ) )
      load_answer = LOAD_TYPE_VIK_SUCCESS;
    else
      load_answer = LOAD_TYPE_VIK_FAILURE_NON_FATAL;
  }
  else if ( a_jpg_magic_check ( filename ) ) {
    if ( ! a_jpg_load_file ( top, filename, vp ) )
      load_answer = LOAD_TYPE_UNSUPPORTED_FAILURE;
  }
  else
  {
	// For all other file types which consist of tracks, routes and/or waypoints,
	//  must be loaded into a new TrackWaypoint layer (hence it be created)
    gboolean success = TRUE; // Detect load failures - mainly to remove the layer created as it's not required

    VikLayer *vtl = vik_layer_create ( VIK_LAYER_TRW, vp, FALSE );
    vik_layer_rename ( vtl, a_file_basename ( filename ) );

    // In fact both kml & gpx files start the same as they are in xml
    if ( a_file_check_ext ( filename, ".kml" ) && check_magic ( f, GPX_MAGIC ) ) {
      // Implicit Conversion
      if ( ! ( success = a_babel_convert_from ( VIK_TRW_LAYER(vtl), "-i kml", filename, NULL, NULL, NULL ) ) ) {
        load_answer = LOAD_TYPE_GPSBABEL_FAILURE;
      }
    }
    // NB use a extension check first, as a GPX file header may have a Byte Order Mark (BOM) in it
    //    - which currently confuses our check_magic function
    else if ( a_file_check_ext ( filename, ".gpx" ) || check_magic ( f, GPX_MAGIC ) ) {
      if ( ! ( success = a_gpx_read_file ( VIK_TRW_LAYER(vtl), f ) ) ) {
        load_answer = LOAD_TYPE_GPX_FAILURE;
      }
    }
    else {
      // Try final supported file type
      if ( ! ( success = a_gpspoint_read_file ( VIK_TRW_LAYER(vtl), f, dirpath ) ) ) {
        // Failure here means we don't know how to handle the file
        load_answer = LOAD_TYPE_UNSUPPORTED_FAILURE;
      }
    }
    g_free ( dirpath );

    // Clean up when we can't handle the file
    if ( ! success ) {
      // free up layer
      g_object_unref ( vtl );
    }
    else {
      // Complete the setup from the successful load
      vik_layer_post_read ( vtl, vp, TRUE );
      vik_aggregate_layer_add_layer ( top, vtl, FALSE );
      vik_trw_layer_auto_set_view ( VIK_TRW_LAYER(vtl), vp );
    }
  }
  xfclose(f);
  return load_answer;
}
/**
 * Correlate the image to any track within the TrackWaypoint layer
 */
static void trw_layer_geotag_process ( geotag_options_t *options )
{
	if ( !options->vtl || !IS_VIK_LAYER(options->vtl) )
		return;

	if ( !options->image )
		return;

	gboolean has_gps_exif = FALSE;
	gchar* datetime = a_geotag_get_exif_date_from_file ( options->image, &has_gps_exif );

	if ( datetime ) {
	
		// If image already has gps info - don't attempt to change it.
		if ( !options->ov.overwrite_gps_exif && has_gps_exif ) {
			if ( options->ov.create_waypoints ) {
				// Create waypoint with file information
				gchar *name = NULL;
				VikWaypoint *wp = a_geotag_create_waypoint_from_file ( options->image, vik_trw_layer_get_coord_mode (options->vtl), &name );
				if ( !name )
					name = g_strdup ( a_file_basename ( options->image ) );
				vik_trw_layer_filein_add_waypoint ( options->vtl, name, wp );
				g_free ( name );
				
				// Mark for redraw
				options->redraw = TRUE;
			}
			g_free ( datetime );
			return;
		}

		options->PhotoTime = ConvertToUnixTime ( datetime, EXIF_DATE_FORMAT, options->ov.TimeZoneHours, options->ov.TimeZoneMins);
		g_free ( datetime );
		
		// Apply any offset
		options->PhotoTime = options->PhotoTime + options->ov.time_offset;

		options->found_match = FALSE;

		if ( options->track ) {
			// Single specified track
			// NB Doesn't care about track name
			trw_layer_geotag_track ( NULL, options->track, options );
		}
		else {
			// Try all tracks
			GHashTable *tracks = vik_trw_layer_get_tracks ( options->vtl );
			if ( g_hash_table_size (tracks) > 0 ) {
				g_hash_table_foreach ( tracks, (GHFunc) trw_layer_geotag_track, options );
			}
		}

		// Match found ?
		if ( options->found_match ) {

			if ( options->ov.create_waypoints ) {

				// Create waypoint with found position
				gchar *name = NULL;
				VikWaypoint *wp = a_geotag_create_waypoint_positioned ( options->image, options->coord, options->altitude, &name );
				if ( !name )
					name = g_strdup ( a_file_basename ( options->image ) );
				vik_trw_layer_filein_add_waypoint ( options->vtl, name, wp );
				g_free ( name );
				
				// Mark for redraw
				options->redraw = TRUE;
			}

			// Write EXIF if specified
			if ( options->ov.write_exif ) {
				a_geotag_write_exif_gps ( options->image, options->coord, options->altitude, options->ov.no_change_mtime );
			}
		}
	}
}