summaryrefslogtreecommitdiff
path: root/navit
diff options
context:
space:
mode:
authormartin-s <martin-s@ffa7fe5e-494d-0410-b361-a75ebd5db220>2010-01-04 09:13:07 +0000
committermartin-s <martin-s@ffa7fe5e-494d-0410-b361-a75ebd5db220>2010-01-04 09:13:07 +0000
commit425dec68f8799e1ee36549c6c8a2c399f8fc6b40 (patch)
tree7951dcdb7513d2c28db5781d7c7034877d6cbb4d /navit
parent771e741ee77bb84cc4d112ca6671addfefe99d6a (diff)
downloadnavit-425dec68f8799e1ee36549c6c8a2c399f8fc6b40.tar.gz
Add:gui_internal:More html functionality
git-svn-id: http://svn.code.sf.net/p/navit/code/trunk/navit@2895 ffa7fe5e-494d-0410-b361-a75ebd5db220
Diffstat (limited to 'navit')
-rw-r--r--navit/attr.c28
-rw-r--r--navit/attr.h1
-rw-r--r--navit/attr_def.h3
-rw-r--r--navit/command.c12
-rw-r--r--navit/gui/internal/gui_internal.c290
-rw-r--r--navit/gui/internal/gui_internal.h1
-rw-r--r--navit/navit.c2
7 files changed, 290 insertions, 47 deletions
diff --git a/navit/attr.c b/navit/attr.c
index ad9013d0d..79458e90e 100644
--- a/navit/attr.c
+++ b/navit/attr.c
@@ -504,23 +504,29 @@ attr_free(struct attr *attr)
g_free(attr);
}
-struct attr *
-attr_dup(struct attr *attr)
+void
+attr_dup_content(struct attr *src, struct attr *dst)
{
int size;
- struct attr *ret=g_new0(struct attr, 1);
- ret->type=attr->type;
- if (attr->type >= attr_type_int_begin && attr->type <= attr_type_int_end)
- ret->u.num=attr->u.num;
- else if (attr->type >= attr_type_object_begin && attr->type <= attr_type_object_end)
- ret->u.data=attr->u.data;
+ dst->type=src->type;
+ if (src->type >= attr_type_int_begin && src->type <= attr_type_int_end)
+ dst->u.num=src->u.num;
+ else if (src->type >= attr_type_object_begin && src->type <= attr_type_object_end)
+ dst->u.data=src->u.data;
else {
- size=attr_data_size(attr);
+ size=attr_data_size(src);
if (size) {
- ret->u.data=g_malloc(size);
- memcpy(ret->u.data, attr->u.data, size);
+ dst->u.data=g_malloc(size);
+ memcpy(dst->u.data, src->u.data, size);
}
}
+}
+
+struct attr *
+attr_dup(struct attr *attr)
+{
+ struct attr *ret=g_new0(struct attr, 1);
+ attr_dup_content(attr, ret);
return ret;
}
diff --git a/navit/attr.h b/navit/attr.h
index b6db5a7ec..5c2ec8132 100644
--- a/navit/attr.h
+++ b/navit/attr.h
@@ -156,6 +156,7 @@ void *attr_data_get(struct attr *attr);
void attr_data_set(struct attr *attr, void *data);
void attr_data_set_le(struct attr *attr, void *data);
void attr_free(struct attr *attr);
+void attr_dup_content(struct attr *src, struct attr *dst);
struct attr *attr_dup(struct attr *attr);
void attr_list_free(struct attr **attrs);
struct attr **attr_list_dup(struct attr **attrs);
diff --git a/navit/attr_def.h b/navit/attr_def.h
index 461c0a197..940304249 100644
--- a/navit/attr_def.h
+++ b/navit/attr_def.h
@@ -276,6 +276,9 @@ ATTR(daylayout)
ATTR(nightlayout)
ATTR(xml_text)
ATTR(layout_name)
+ATTR(user_name)
+ATTR(user_pass)
+ATTR(status_text)
ATTR2(0x0003ffff,type_string_end)
ATTR2(0x00040000,type_special_begin)
ATTR(order)
diff --git a/navit/command.c b/navit/command.c
index a9e13fd3e..4d830820f 100644
--- a/navit/command.c
+++ b/navit/command.c
@@ -396,10 +396,16 @@ command_call_function(struct context *ctx, struct result *res)
} else {
if (command_object_get_attr(ctx, &res->attr, attr_callback_list, &cbl)) {
int valid;
+ struct attr **out=NULL;
dbg(1,"function call %s from %s\n",function, attr_to_name(res->attr.type));
- callback_list_call_attr_4(cbl.u.callback_list, attr_command, function, list, NULL, &valid);
- }
- res->attr.type=attr_none;
+ callback_list_call_attr_4(cbl.u.callback_list, attr_command, function, list, &out, &valid);
+ if (out && out[0]) {
+ attr_dup_content(out[0], &res->attr);
+ attr_list_free(out);
+ } else
+ res->attr.type=attr_none;
+ } else
+ res->attr.type=attr_none;
}
res->var=NULL;
res->varlen=0;
diff --git a/navit/gui/internal/gui_internal.c b/navit/gui/internal/gui_internal.c
index adc5a6cd7..653298c3c 100644
--- a/navit/gui/internal/gui_internal.c
+++ b/navit/gui/internal/gui_internal.c
@@ -71,6 +71,10 @@
#include "xmlconfig.h"
#include "util.h"
+struct form {
+ char *onsubmit;
+};
+
struct menu_data {
struct widget *search_list;
struct widget *keyboard;
@@ -136,6 +140,7 @@ struct widget {
*/
int cols;
enum flags flags;
+ int flags2;
void *instance;
int (*set_attr)(void *, struct attr *);
int (*get_attr)(void *, enum attr_type, struct attr *, struct attr_iter *);
@@ -147,6 +152,7 @@ struct widget {
int is_on;
int redraw;
struct menu_data *menu_data;
+ struct form *form;
GList *children;
};
@@ -234,7 +240,7 @@ struct gui_priv {
int widgets_count;
int redraw;
struct widget root;
- struct widget *highlighted;
+ struct widget *highlighted,*editable;
struct widget *highlighted_menu;
int clickp_valid, vehicle_valid;
struct pcoord clickp, vehiclep;
@@ -246,6 +252,7 @@ struct gui_priv {
char *country_iso2;
int speech;
int keyboard;
+ int keyboard_required;
/**
* The setting information read from the configuration file.
* values of -1 indicate no value was specified in the config file.
@@ -276,6 +283,7 @@ struct gui_priv {
int html_skip;
char *html_anchor;
int html_anchor_found;
+ struct form *form;
struct html {
int skip;
enum html_tag {
@@ -285,11 +293,15 @@ struct gui_priv {
html_tag_html,
html_tag_img,
html_tag_script,
+ html_tag_form,
+ html_tag_input,
+ html_tag_div,
} tag;
char *command;
char *name;
char *href;
struct widget *w;
+ struct widget *container;
} html[10];
};
@@ -302,6 +314,9 @@ struct html_tag_map {
{"html",html_tag_html},
{"img",html_tag_img},
{"script",html_tag_script},
+ {"form",html_tag_form},
+ {"input",html_tag_input},
+ {"div",html_tag_div},
};
@@ -639,14 +654,25 @@ gui_internal_label_render(struct gui_priv *this, struct widget *w)
{
struct point pnt=w->p;
gui_internal_background_render(this, w);
+ if (w->state & STATE_EDIT)
+ graphics_draw_rectangle(this->gra, this->highlight_background, &pnt, w->w, w->h);
if (w->text) {
+ char *text,startext[strlen(w->text)+1];
+ text=w->text;
+ if (w->flags2 & 1) {
+ int i;
+ for (i = 0 ; i < strlen(text); i++)
+ startext[i]='*';
+ startext[i]='\0';
+ text=startext;
+ }
if (w->flags & gravity_right) {
pnt.y+=w->h-this->spacing;
pnt.x+=w->w-w->textw-this->spacing;
- graphics_draw_text(this->gra, w->foreground, w->text_background, this->fonts[w->font_idx], w->text, &pnt, 0x10000, 0x0);
+ graphics_draw_text(this->gra, w->foreground, w->text_background, this->fonts[w->font_idx], text, &pnt, 0x10000, 0x0);
} else {
pnt.y+=w->h-this->spacing;
- graphics_draw_text(this->gra, w->foreground, w->text_background, this->fonts[w->font_idx], w->text, &pnt, 0x10000, 0x0);
+ graphics_draw_text(this->gra, w->foreground, w->text_background, this->fonts[w->font_idx], text, &pnt, 0x10000, 0x0);
}
}
}
@@ -887,6 +913,19 @@ static void gui_internal_highlight(struct gui_priv *this)
if (this->current.x > -1 && this->current.y > -1) {
menu=g_list_last(this->root.children)->data;
found=gui_internal_find_widget(menu, &this->current, STATE_SENSITIVE);
+ if (!found) {
+ found=gui_internal_find_widget(menu, &this->current, STATE_EDITABLE);
+ if (found) {
+ if (this->editable && this->editable != found) {
+ this->editable->state &= ~ STATE_EDIT;
+ gui_internal_widget_render(this, this->editable);
+ }
+ found->state |= STATE_EDIT;
+ gui_internal_widget_render(this, found);
+ this->editable=found;
+ found=NULL;
+ }
+ }
}
gui_internal_highlight_do(this, found);
this->motion_timeout_event=NULL;
@@ -1872,7 +1911,7 @@ gui_internal_cmd_add_bookmark2(struct gui_priv *this, struct widget *wm, void *d
we=gui_internal_box_new(this, gravity_left_center|orientation_horizontal|flags_fill);
gui_internal_widget_append(w, we);
gui_internal_widget_append(we, wk=gui_internal_label_new(this, name));
- wk->state |= STATE_EDIT|STATE_CLEAR;
+ wk->state |= STATE_EDIT|STATE_EDITABLE|STATE_CLEAR;
wk->background=this->background;
wk->flags |= flags_expand|flags_fill;
wk->func = gui_internal_cmd_add_bookmark_changed;
@@ -3242,7 +3281,7 @@ gui_internal_search(struct gui_priv *this, char *what, char *type, int flags)
wl=gui_internal_box_new(this, gravity_left_top|orientation_vertical|flags_expand|flags_fill);
gui_internal_widget_append(wr, wl);
gui_internal_menu_data(this)->search_list=wl;
- wk->state |= STATE_EDIT;
+ wk->state |= STATE_EDIT|STATE_EDITABLE;
wk->background=this->background;
wk->flags |= flags_expand|flags_fill;
wk->func = gui_internal_search_changed;
@@ -3581,9 +3620,9 @@ gui_internal_add_vehicle_profile(struct gui_priv *this, struct widget
name = attr->u.str;
// Determine whether the profile is the active one
- vehicle_get_attr(v, attr_profilename, &profile_attr, NULL);
- active_profile = profile_attr.u.str;
- active = strcmp(name, active_profile) == 0;
+ if (vehicle_get_attr(v, attr_profilename, &profile_attr, NULL))
+ active_profile = profile_attr.u.str;
+ active = active_profile != NULL && !strcmp(name, active_profile);
dbg(0, "Adding vehicle profile %s, active=%s/%i\n", name,
active_profile, active);
@@ -3771,14 +3810,134 @@ gui_internal_html_command(struct gui_priv *this, struct widget *w, void *data)
}
static void
+gui_internal_html_submit_set(struct gui_priv *this, struct widget *w, struct form *form)
+{
+ GList *l;
+ if (w->form == form && w->name) {
+ struct attr *attr=attr_new_from_text(w->name, w->text?w->text:"");
+ if (attr)
+ gui_set_attr(this->self.u.gui, attr);
+ attr_free(attr);
+ }
+ l=w->children;
+ while (l) {
+ w=l->data;
+ gui_internal_html_submit_set(this, w, form);
+ l=g_list_next(l);
+ }
+
+}
+
+static void
+gui_internal_html_submit(struct gui_priv *this, struct widget *w, void *data)
+{
+ struct widget *menu;
+ GList *l;
+
+ dbg(1,"enter form %p %s\n",w->form,w->form->onsubmit);
+ l=g_list_last(this->root.children);
+ menu=l->data;
+ graphics_draw_mode(this->gra, draw_mode_begin);
+ gui_internal_highlight_do(this, NULL);
+ gui_internal_menu_render(this);
+ graphics_draw_mode(this->gra, draw_mode_end);
+ gui_internal_html_submit_set(this, menu, w->form);
+ gui_internal_evaluate(this,w->form->onsubmit);
+}
+
+static void
+gui_internal_html_load_href(struct gui_priv *this, char *href, int replace)
+{
+ if (replace)
+ gui_internal_prune_menu_count(this, 1, 0);
+ if (href && href[0] == '#') {
+ dbg(1,"href=%s\n",href);
+ gui_internal_html_menu(this, this->html_text, href+1);
+ }
+}
+
+static void
gui_internal_html_href(struct gui_priv *this, struct widget *w, void *data)
{
- if (w->command && w->command[0] == '#') {
- dbg(1,"href=%s\n",w->command);
- gui_internal_html_menu(this, this->html_text, w->command+1);
+ gui_internal_html_load_href(this, w->command, 0);
+}
+
+struct div_flags_map {
+ char *attr;
+ char *val;
+ enum flags flags;
+} div_flags_map[] = {
+ {"gravity","none",gravity_none},
+ {"gravity","left",gravity_left},
+ {"gravity","xcenter",gravity_xcenter},
+ {"gravity","right",gravity_right},
+ {"gravity","top",gravity_top},
+ {"gravity","ycenter",gravity_ycenter},
+ {"gravity","bottom",gravity_bottom},
+ {"gravity","left_top",gravity_left_top},
+ {"gravity","top_center",gravity_top_center},
+ {"gravity","right_top",gravity_right_top},
+ {"gravity","left_center",gravity_left_center},
+ {"gravity","center",gravity_center},
+ {"gravity","right_center",gravity_right_center},
+ {"gravity","left_bottom",gravity_left_bottom},
+ {"gravity","bottom_center",gravity_bottom_center},
+ {"gravity","right_bottom",gravity_right_bottom},
+ {"expand","1",flags_expand},
+ {"fill","1",flags_fill},
+ {"orientation","horizontal",orientation_horizontal},
+ {"orientation","vertical",orientation_vertical},
+ {"orientation","horizontal_vertical",orientation_horizontal_vertical},
+};
+
+static enum flags
+div_flag(const char **names, const char **values, char *name)
+{
+ int i;
+ enum flags ret=0;
+ const char *value=find_attr(names, values, name);
+ if (!value)
+ return ret;
+ for (i = 0 ; i < sizeof(div_flags_map)/sizeof(struct div_flags_map); i++) {
+ if (!strcmp(div_flags_map[i].attr,name) && !strcmp(div_flags_map[i].val,value))
+ ret|=div_flags_map[i].flags;
}
+ return ret;
}
+static enum flags
+div_flags(const char **names, const char **values)
+{
+ enum flags flags;
+ flags = div_flag(names, values, "gravity");
+ flags |= div_flag(names, values, "orientation");
+ flags |= div_flag(names, values, "expand");
+ flags |= div_flag(names, values, "fill");
+ return flags;
+}
+
+static struct widget *
+html_image(struct gui_priv *this, const char **names, const char **values)
+{
+ const char *src, *size;
+ struct graphics_image *img=NULL;
+
+ src=find_attr(names, values, "src");
+ if (!src)
+ return NULL;
+ size=find_attr(names, values, "size");
+ if (!size)
+ size="l";
+ if (!strcmp(size,"l"))
+ img=image_new_l(this, src);
+ else if (!strcmp(size,"s"))
+ img=image_new_s(this, src);
+ else if (!strcmp(size,"xs"))
+ img=image_new_xs(this, src);
+ if (!img)
+ return NULL;
+ return gui_internal_image_new(this, img);
+}
static void
gui_internal_html_start(void *dummy, const char *tag_name, const char **names, const char **values, void *data, void *error)
@@ -3787,7 +3946,7 @@ gui_internal_html_start(void *dummy, const char *tag_name, const char **names, c
int i;
enum html_tag tag=html_tag_none;
struct html *html=&this->html[this->html_depth];
- const char *src, *cond;
+ const char *cond, *type;
if (!strcasecmp(tag_name,"text"))
return;
@@ -3822,9 +3981,45 @@ gui_internal_html_start(void *dummy, const char *tag_name, const char **names, c
break;
case html_tag_img:
html->command=find_attr_dup(names, values, "onclick");
- src=find_attr(names, values, "src");
- if (src)
- html->w=gui_internal_image_new(this, image_new_l(this, src));
+ html->w=html_image(this, names, values);
+ break;
+ case html_tag_form:
+ this->form=g_new0(struct form, 1);
+ this->form->onsubmit=find_attr_dup(names, values, "onsubmit");
+ break;
+ case html_tag_input:
+ type=find_attr_dup(names, values, "type");
+ if (!type)
+ break;
+ if (!strcmp(type,"image")) {
+ html->w=html_image(this, names, values);
+ if (html->w) {
+ html->w->state|=STATE_SENSITIVE;
+ html->w->func=gui_internal_html_submit;
+ }
+ }
+ if (!strcmp(type,"text") || !strcmp(type,"password")) {
+ html->w=gui_internal_label_new(this, NULL);
+ html->w->background=this->background;
+ html->w->flags |= div_flags(names, values);
+ html->w->state|=STATE_EDITABLE;
+ if (!this->editable) {
+ this->editable=html->w;
+ html->w->state|=STATE_EDIT;
+ }
+ this->keyboard_required=1;
+ if (!strcmp(type,"password"))
+ html->w->flags2 |= 1;
+ }
+ if (html->w) {
+ html->w->form=this->form;
+ html->w->name=find_attr_dup(names, values, "name");
+ }
+ break;
+ case html_tag_div:
+ html->w=gui_internal_box_new(this, div_flags(names, values));
+ html->container=this->html_container;
+ this->html_container=html->w;
break;
default:
break;
@@ -3862,9 +4057,15 @@ gui_internal_html_end(void *dummy, const char *tag_name, void *data, void *error
html->w->func=gui_internal_html_href;
}
switch (html->tag) {
+ case html_tag_div:
+ this->html_container=html->container;
case html_tag_img:
+ case html_tag_input:
gui_internal_widget_append(this->html_container, html->w);
break;
+ case html_tag_form:
+ this->form=NULL;
+ break;
default:
break;
}
@@ -3903,13 +4104,15 @@ gui_internal_html_text(void *dummy, const char *text, int len, void *data, void
switch (html->tag) {
case html_tag_a:
if (html->name && len) {
- this->html_container=gui_internal_menu(this, gettext(text_stripped));
+ this->html_container=gui_internal_box_new(this, gravity_center|orientation_horizontal_vertical|flags_expand|flags_fill);
+ gui_internal_widget_append(gui_internal_menu(this, gettext(text_stripped)), this->html_container);
this->html_container->spx=this->spacing*10;
}
break;
case html_tag_h1:
if (!this->html_container) {
- this->html_container=gui_internal_menu(this, gettext(text_stripped));
+ this->html_container=gui_internal_box_new(this, gravity_center|orientation_horizontal_vertical|flags_expand|flags_fill);
+ gui_internal_widget_append(gui_internal_menu(this, gettext(text_stripped)), this->html_container);
this->html_container->spx=this->spacing*10;
}
break;
@@ -3921,6 +4124,11 @@ gui_internal_html_text(void *dummy, const char *text, int len, void *data, void
html->w=w;
}
break;
+ case html_tag_div:
+ if (len) {
+ gui_internal_widget_append(html->w, gui_internal_text_new(this, gettext(text_stripped), gravity_center|orientation_vertical));
+ }
+ break;
case html_tag_script:
dbg(1,"execute %s\n",text_stripped);
gui_internal_evaluate(this,text_stripped);
@@ -3933,22 +4141,27 @@ gui_internal_html_text(void *dummy, const char *text, int len, void *data, void
static void
gui_internal_html_menu(struct gui_priv *this, const char *document, char *anchor)
{
+ char *doc=g_strdup(document);
graphics_draw_mode(this->gra, draw_mode_begin);
this->html_container=NULL;
this->html_depth=0;
this->html_anchor=anchor;
this->html_anchor_found=0;
- xml_parse_text(document, this, gui_internal_html_start, gui_internal_html_end, gui_internal_html_text);
+ this->form=NULL;
+ this->keyboard_required=0;
+ this->editable=NULL;
+ callback_list_call_attr_2(this->cbl,attr_gui,anchor,&doc);
+ xml_parse_text(doc, this, gui_internal_html_start, gui_internal_html_end, gui_internal_html_text);
+ g_free(doc);
+ if (this->keyboard_required && this->keyboard) {
+ this->html_container->flags=gravity_center|orientation_vertical|flags_expand|flags_fill;
+ gui_internal_widget_append(this->html_container, gui_internal_keyboard(this,2));
+ }
gui_internal_menu_render(this);
graphics_draw_mode(this->gra, draw_mode_end);
}
-static void gui_internal_menu_root(struct gui_priv *this)
-{
- gui_internal_html_menu(this, this->html_text, "Main Menu");
-}
-
static void
gui_internal_enter(struct gui_priv *this, int ignore)
{
@@ -3970,7 +4183,7 @@ gui_internal_leave(struct gui_priv *this)
}
static void
-gui_internal_cmd_menu(struct gui_priv *this, struct point *p, int ignore)
+gui_internal_cmd_menu(struct gui_priv *this, struct point *p, int ignore, char *href)
{
struct transformation *trans;
struct coord c;
@@ -4005,15 +4218,26 @@ gui_internal_cmd_menu(struct gui_priv *this, struct point *p, int ignore)
this->vehicle_valid=1;
}
// draw menu
- gui_internal_menu_root(this);
+ gui_internal_html_load_href(this, href?href:"#Main Menu", 0);
}
static void
-gui_internal_cmd_menu2(struct gui_priv *this)
+gui_internal_cmd_menu2(struct gui_priv *this, char *function, struct attr **in, struct attr ***out, int *valid)
{
- if (this->root.children)
+ char *href=NULL;
+ int replace=0;
+ if (in && in[0] && ATTR_IS_STRING(in[0]->type)) {
+ href=in[0]->u.str;
+ if (in[1] && ATTR_IS_INT(in[1]->type))
+ replace=in[1]->u.num;
+ }
+ if (this->root.children) {
+ if (!href)
+ return;
+ gui_internal_html_load_href(this, href, replace);
return;
- gui_internal_cmd_menu(this, NULL, 0);
+ }
+ gui_internal_cmd_menu(this, NULL, 0, href);
}
@@ -4059,7 +4283,7 @@ gui_internal_cmd_log(struct gui_priv *this)
we=gui_internal_box_new(this, gravity_left_center|orientation_horizontal|flags_fill);
gui_internal_widget_append(w, we);
gui_internal_widget_append(we, wk=gui_internal_label_new(this, _("Message")));
- wk->state |= STATE_EDIT|STATE_CLEAR;
+ wk->state |= STATE_EDIT|STATE_EDITABLE|STATE_CLEAR;
wk->background=this->background;
wk->flags |= flags_expand|flags_fill;
wk->func = gui_internal_cmd_log_changed;
@@ -4146,7 +4370,7 @@ gui_internal_set_attr(struct gui_priv *this, struct attr *attr)
return 1;
default:
dbg(0,"%s\n",attr_to_name(attr->type));
- return 0;
+ return 1;
}
}
@@ -4206,7 +4430,7 @@ static void gui_internal_button(void *data, int pressed, int button, struct poin
if (button != 1)
return;
if (this->menu_on_map_click) {
- gui_internal_cmd_menu(this, p, 0);
+ gui_internal_cmd_menu(this, p, 0, NULL);
return;
}
if (this->signal_on_map_click) {
@@ -4279,7 +4503,7 @@ static void gui_internal_resize(void *data, int w, int h)
if (this->root.children) {
if (changed) {
gui_internal_prune_menu(this, NULL);
- gui_internal_menu_root(this);
+ gui_internal_html_load_href(this, "#Main Menu", 0);
} else {
gui_internal_menu_render(this);
}
@@ -4423,7 +4647,7 @@ static void gui_internal_keypress(void *data, char *key)
break;
case NAVIT_KEY_RETURN:
case NAVIT_KEY_MENU:
- gui_internal_cmd_menu(this, NULL, 0);
+ gui_internal_cmd_menu(this, NULL, 0, NULL);
break;
}
return;
diff --git a/navit/gui/internal/gui_internal.h b/navit/gui/internal/gui_internal.h
index 80f57f8f7..936327509 100644
--- a/navit/gui/internal/gui_internal.h
+++ b/navit/gui/internal/gui_internal.h
@@ -7,6 +7,7 @@ struct graphics_image;
#define STATE_SENSITIVE 8
#define STATE_EDIT 16
#define STATE_CLEAR 32
+#define STATE_EDITABLE 64
enum widget_type {
widget_box=1,
diff --git a/navit/navit.c b/navit/navit.c
index f06bc6747..eb92e8bee 100644
--- a/navit/navit.c
+++ b/navit/navit.c
@@ -2327,6 +2327,8 @@ navit_layout_switch(struct navit *n)
if (navit_get_attr(n,attr_layout,&layout_attr,NULL)!=1) {
return; //No layout - nothing to switch
}
+ if (!n->vehicle)
+ return;
l=layout_attr.u.layout;
if (l->dayname || l->nightname) {