Merge pull request #8147 from osmandapp/exit_and_shield_widget

Exit and shield widget
This commit is contained in:
vshcherb 2020-01-09 17:00:38 +01:00 committed by GitHub
commit b7d515e98a
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
17 changed files with 626 additions and 125 deletions

View file

@ -677,6 +677,71 @@ public class RouteDataObject {
return false; return false;
} }
public boolean isExitPoint() {
if (pointTypes != null) {
int ptSz = pointTypes.length;
for (int i = 0; i < ptSz; i++) {
int[] point = pointTypes[i];
if (point != null) {
int pSz = point.length;
for (int j = 0; j < pSz; j++) {
if (region.routeEncodingRules.get(point[j]).getValue().equals("motorway_junction")) {
return true;
}
}
}
}
}
return false;
}
// public boolean isMotorWayLink() {
// int sz = types.length;
// for (int i = 0; i < sz; i++) {
// RouteTypeRule r = region.quickGetEncodingRule(types[i]);
// if (r.getTag().equals("highway") && r.getValue().equals("motorway_link")) {
// return true;
// }
// }
// return false;
// }
public String getExitName() {
if (pointNames != null && pointNameTypes != null) {
int pnSz = pointNames.length;
for (int i = 0; i < pnSz; i++) {
String[] point = pointNames[i];
if (point != null) {
int pSz = point.length;
for (int j = 0; j < pSz; j++) {
if (pointNameTypes[i][j] == region.nameTypeRule) {
return point[j];
}
}
}
}
}
return null;
}
public String getExitRef() {
if (pointNames != null && pointNameTypes != null) {
int pnSz = pointNames.length;
for (int i = 0; i < pnSz; i++) {
String[] point = pointNames[i];
if (point != null) {
int pSz = point.length;
for (int j = 0; j < pSz; j++) {
if (pointNameTypes[i][j] == region.refTypeRule) {
return point[j];
}
}
}
}
}
return null;
}
public int getOneway() { public int getOneway() {
int sz = types.length; int sz = types.length;
for (int i = 0; i < sz; i++) { for (int i = 0; i < sz; i++) {

View file

@ -0,0 +1,25 @@
package net.osmand.router;
public class ExitInfo {
private String ref;
private String exitStreetName;
public String getRef() {
return ref;
}
public void setRef(String ref) {
this.ref = ref;
}
public String getExitStreetName() {
return exitStreetName;
}
public void setExitStreetName(String exitStreetName) {
this.exitStreetName = exitStreetName;
}
}

View file

@ -0,0 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="@color/active_color_primary_light" />
<corners android:radius="3dp" />
</shape>

View file

@ -335,43 +335,74 @@
android:background="@drawable/btn_round" android:background="@drawable/btn_round"
android:minHeight="@dimen/map_address_height"> android:minHeight="@dimen/map_address_height">
<FrameLayout <LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_marginLeft="5dp"
android:layout_marginRight="5dp"
android:gravity="center"
android:orientation="horizontal">
<TextView
android:id="@+id/map_exit_ref"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_gravity="center" android:background="@drawable/bg_topbar_shield_exit_ref"
android:layout_marginLeft="5dp" android:gravity="center"
android:layout_marginRight="5dp" android:minWidth="@dimen/map_widget_height"
> android:textColor="@color/color_white"
android:textSize="@dimen/map_widget_text_size"
android:visibility="gone"
tools:text="8"
tools:visibility="visible" />
<TextView <ImageView
android:id="@+id/map_address_text_shadow" android:id="@+id/map_turn_icon"
android:importantForAccessibility="no" android:layout_width="@dimen/map_widget_height"
android:layout_height="@dimen/map_widget_height"
android:scaleType="fitCenter"
tools:src="@drawable/map_turn_right_small" />
<ImageView
android:id="@+id/map_shield_icon"
android:layout_width="60dp"
android:layout_height="match_parent"
android:scaleType="fitCenter"
tools:src="@drawable/h_white_pillow_2_road_shield" />
<FrameLayout
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content">
android:layout_gravity="center"
android:ellipsize="end"
android:maxLines="1"
android:singleLine="true"
android:textColor="@color/color_black"
android:textSize="@dimen/map_widget_text_size"
tools:text="Long Street Name">
</TextView>
<TextView <TextView
android:id="@+id/map_address_text" android:id="@+id/map_address_text_shadow"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_gravity="center" android:layout_gravity="center"
android:ellipsize="end" android:ellipsize="end"
android:maxLines="1" android:importantForAccessibility="no"
android:singleLine="true" android:maxLines="1"
android:textColor="@color/color_black" android:singleLine="true"
android:textSize="@dimen/map_widget_text_size" android:textColor="@color/color_black"
tools:text="Long Street Name"> android:textSize="@dimen/map_widget_text_size"
</TextView> tools:text="Long Street Name" />
<TextView
android:id="@+id/map_address_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:ellipsize="end"
android:maxLines="1"
android:singleLine="true"
android:textColor="@color/color_black"
android:textSize="@dimen/map_widget_text_size"
tools:text="Long Street Name" />
</FrameLayout> </FrameLayout>
</LinearLayout>
<LinearLayout <LinearLayout
android:id="@+id/waypoint_info_bar" android:id="@+id/waypoint_info_bar"

View file

@ -112,43 +112,81 @@
android:background="@drawable/btn_flat" android:background="@drawable/btn_flat"
android:minHeight="@dimen/map_address_height"> android:minHeight="@dimen/map_address_height">
<!-- android:layout_weight="1" to show properly next turn --> <!-- android:layout_weight="1" to show properly next turn -->
<FrameLayout <LinearLayout
android:layout_width="wrap_content" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_gravity="center" android:layout_gravity="center"
android:layout_marginLeft="5dp" android:layout_marginLeft="5dp"
android:layout_marginRight="5dp"> android:layout_marginRight="5dp"
android:gravity="center"
android:orientation="horizontal">
<TextView
android:id="@+id/map_exit_ref"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="@drawable/bg_topbar_shield_exit_ref"
android:gravity="center"
android:minWidth="@dimen/map_widget_height"
android:textColor="@color/color_white"
android:textSize="@dimen/map_widget_text_size"
android:visibility="gone"
android:paddingLeft="@dimen/text_margin_small"
android:paddingRight="@dimen/text_margin_small"
android:textStyle="bold"
tools:text="8"
<TextView tools:visibility="visible" />
android:id="@+id/map_address_text_shadow"
android:importantForAccessibility="no"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:ellipsize="end"
android:maxLines="1"
android:singleLine="true"
android:textColor="@color/color_black"
android:textSize="@dimen/map_widget_text_size"
tools:text="Long Street Name">
</TextView>
<TextView <ImageView
android:id="@+id/map_address_text" android:id="@+id/map_turn_icon"
android:layout_width="wrap_content" android:layout_width="@dimen/map_widget_height"
android:layout_height="wrap_content" android:layout_height="@dimen/map_widget_height"
android:layout_gravity="center" android:scaleType="fitCenter"
android:ellipsize="end" android:visibility="gone"
android:maxLines="1" tools:src="@drawable/map_turn_right_small" />
android:singleLine="true"
android:textColor="@color/color_black"
android:textSize="@dimen/map_widget_text_size"
tools:text="Long Street Name">
</TextView>
</FrameLayout>
<ImageView
android:id="@+id/map_shield_icon"
android:layout_width="@dimen/map_widget_height"
android:layout_height="@dimen/map_widget_height"
android:scaleType="fitCenter"
android:visibility="gone"
tools:src="@drawable/h_white_pillow_2_road_shield" />
<FrameLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<TextView
android:id="@+id/map_address_text_shadow"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:ellipsize="end"
android:importantForAccessibility="no"
android:maxLines="1"
android:singleLine="true"
android:textColor="@color/color_black"
android:textSize="@dimen/map_widget_text_size"
tools:text="Long Street Name" />
<TextView
android:id="@+id/map_address_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:ellipsize="end"
android:maxLines="1"
android:singleLine="true"
android:textColor="@color/color_black"
android:textSize="@dimen/map_widget_text_size"
tools:text="Long Street Name" />
</FrameLayout>
</LinearLayout>
<LinearLayout <LinearLayout
android:id="@+id/waypoint_info_bar" android:id="@+id/waypoint_info_bar"

View file

@ -78,19 +78,36 @@
tools:text="@string/app_version"/> tools:text="@string/app_version"/>
</LinearLayout> </LinearLayout>
<net.osmand.plus.widgets.TextViewEx <LinearLayout
android:id="@+id/description"
android:layout_width="0dp" android:layout_width="0dp"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginRight="5dp"
android:layout_marginTop="8dp"
android:layout_marginBottom="8dp"
android:layout_gravity="center_vertical" android:layout_gravity="center_vertical"
android:layout_marginTop="@dimen/content_padding_half"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:layout_marginBottom="@dimen/content_padding_half"
android:layout_weight="1" android:layout_weight="1"
android:textSize="@dimen/default_desc_text_size" android:orientation="vertical">
android:textColor="?android:textColorPrimary"
tools:text="Head Dmytrivska Street" <net.osmand.plus.widgets.TextViewEx
android:text=""/> android:id="@+id/description"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:text=""
android:textColor="?android:textColorPrimary"
android:textSize="@dimen/default_desc_text_size"
tools:text="Head Dmytrivska Street" />
<ImageView
android:id="@+id/lanes"
android:layout_width="match_parent"
android:layout_height="18dp"
android:layout_marginTop="2dp"
android:scaleType="fitStart"
android:visibility="gone" />
</LinearLayout>
</LinearLayout> </LinearLayout>

View file

@ -49,6 +49,8 @@ import android.graphics.Rect;
import android.graphics.RectF; import android.graphics.RectF;
import android.graphics.Shader; import android.graphics.Shader;
import android.graphics.Shader.TileMode; import android.graphics.Shader.TileMode;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.os.Handler; import android.os.Handler;
import android.os.Looper; import android.os.Looper;
import android.util.DisplayMetrics; import android.util.DisplayMetrics;
@ -389,6 +391,11 @@ public class OsmandRenderer {
} }
} }
public Drawable getShieldDrawable(String shieldId){
Bitmap shield = RenderingIcons.getIcon(context, shieldId, true);
return new BitmapDrawable(context.getResources(),shield);
}
protected void drawBitmap(Canvas cv, Bitmap ico, RectF rf) { protected void drawBitmap(Canvas cv, Bitmap ico, RectF rf) {
if(ico == null) { if(ico == null) {
return; return;

View file

@ -43,7 +43,7 @@ public class TextRenderer {
private Typeface italicTypeface; private Typeface italicTypeface;
private Typeface boldTypeface; private Typeface boldTypeface;
static class TextDrawInfo { public static class TextDrawInfo {
public TextDrawInfo(String text) { public TextDrawInfo(String text) {
this.text = text; this.text = text;
@ -95,6 +95,30 @@ public class TextRenderer {
} }
textOrder = render.getIntPropertyValue(render.ALL.R_TEXT_ORDER, 100); textOrder = render.getIntPropertyValue(render.ALL.R_TEXT_ORDER, 100);
} }
public float getCenterX() {
return centerX;
}
public void setCenterX(float centerX) {
this.centerX = centerX;
}
public float getCenterY() {
return centerY;
}
public void setCenterY(float centerY) {
this.centerY = centerY;
}
public String getShieldResIcon() {
return shieldResIcon;
}
public void setShieldResIcon(String shieldResIcon) {
this.shieldResIcon = shieldResIcon;
}
} }
public TextRenderer(Context context) { public TextRenderer(Context context) {
@ -288,13 +312,13 @@ public class TextRenderer {
} }
} }
private void drawShieldIcon(RenderingContext rc, Canvas cv, TextDrawInfo text, String sr) { public void drawShieldIcon(RenderingContext rc, Canvas cv, TextDrawInfo text, String sr) {
if (sr != null) { if (sr != null) {
float coef = rc.getDensityValue(rc.screenDensityRatio * rc.textScale); float coef = rc.getDensityValue(rc.screenDensityRatio * rc.textScale);
Bitmap ico = RenderingIcons.getIcon(context, sr, true); Bitmap ico = RenderingIcons.getIcon(context, sr, true);
if (ico != null) { if (ico != null) {
float left = text.centerX - ico.getWidth() / 2 * coef - 0.5f; float left = text.centerX - ico.getWidth() / 2 * coef;// - 0.5f;
float top = text.centerY - ico.getHeight() / 2 * coef - paintText.descent() - 0.5f; float top = text.centerY - ico.getHeight() / 2 * coef - paintText.descent() * 1.5f;
if(rc.screenDensityRatio != 1f){ if(rc.screenDensityRatio != 1f){
RectF rf = new RectF(left, top, left + ico.getWidth() * coef, RectF rf = new RectF(left, top, left + ico.getWidth() * coef,
top + ico.getHeight() * coef); top + ico.getHeight() * coef);
@ -308,7 +332,7 @@ public class TextRenderer {
} }
} }
private void drawWrappedText(Canvas cv, TextDrawInfo text, float textSize) { public void drawWrappedText(Canvas cv, TextDrawInfo text, float textSize) {
if (text.textWrap == 0) { if (text.textWrap == 0) {
// set maximum for all text // set maximum for all text
text.textWrap = 40; text.textWrap = 40;

View file

@ -17,6 +17,7 @@ import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.routepreparationmenu.RouteDetailsFragment; import net.osmand.plus.routepreparationmenu.RouteDetailsFragment;
import net.osmand.plus.routing.RouteDirectionInfo; import net.osmand.plus.routing.RouteDirectionInfo;
import net.osmand.plus.views.TurnPathHelper; import net.osmand.plus.views.TurnPathHelper;
import net.osmand.plus.views.mapwidgets.RouteInfoWidgetsFactory;
import net.osmand.util.Algorithms; import net.osmand.util.Algorithms;
import java.util.List; import java.util.List;
@ -67,13 +68,25 @@ public class RouteDirectionsCard extends BaseCard {
TextView timeLabel = (TextView) row.findViewById(R.id.time); TextView timeLabel = (TextView) row.findViewById(R.id.time);
TextView cumulativeDistanceLabel = (TextView) row.findViewById(R.id.cumulative_distance); TextView cumulativeDistanceLabel = (TextView) row.findViewById(R.id.cumulative_distance);
TextView cumulativeTimeLabel = (TextView) row.findViewById(R.id.cumulative_time); TextView cumulativeTimeLabel = (TextView) row.findViewById(R.id.cumulative_time);
ImageView icon = (ImageView) row.findViewById(R.id.direction); ImageView directionIcon = (ImageView) row.findViewById(R.id.direction);
ImageView lanesIcon = (ImageView) row.findViewById(R.id.lanes);
row.findViewById(R.id.divider).setVisibility(directionInfoIndex == directionsInfo.size() - 1 ? View.INVISIBLE : View.VISIBLE); row.findViewById(R.id.divider).setVisibility(directionInfoIndex == directionsInfo.size() - 1 ? View.INVISIBLE : View.VISIBLE);
TurnPathHelper.RouteDrawable drawable = new TurnPathHelper.RouteDrawable(mapActivity.getResources(), true); TurnPathHelper.RouteDrawable drawable = new TurnPathHelper.RouteDrawable(mapActivity.getResources(), true);
drawable.setColorFilter(new PorterDuffColorFilter(getActiveColor(), PorterDuff.Mode.SRC_ATOP)); drawable.setColorFilter(new PorterDuffColorFilter(getActiveColor(), PorterDuff.Mode.SRC_ATOP));
drawable.setRouteType(model.getTurnType()); drawable.setRouteType(model.getTurnType());
icon.setImageDrawable(drawable); directionIcon.setImageDrawable(drawable);
int[] lanes = model.getTurnType().getLanes();
if (lanes != null){
RouteInfoWidgetsFactory.LanesDrawable lanesDrawable = new RouteInfoWidgetsFactory.LanesDrawable(mapActivity,1);
lanesDrawable.lanes = lanes;
lanesDrawable.isTurnByTurn = true;
lanesDrawable.isNightMode = nightMode;
lanesDrawable.updateBounds();
lanesIcon.setImageDrawable(lanesDrawable);
lanesIcon.setVisibility(View.VISIBLE);
}
label.setText(model.getDescriptionRoutePart()); label.setText(model.getDescriptionRoutePart());
if (model.distance > 0) { if (model.distance > 0) {

View file

@ -4,6 +4,7 @@ import android.content.Context;
import android.support.annotation.Nullable; import android.support.annotation.Nullable;
import net.osmand.Location; import net.osmand.Location;
import net.osmand.PlatformUtil;
import net.osmand.binary.BinaryMapRouteReaderAdapter.RouteRegion; import net.osmand.binary.BinaryMapRouteReaderAdapter.RouteRegion;
import net.osmand.binary.BinaryMapRouteReaderAdapter.RouteTypeRule; import net.osmand.binary.BinaryMapRouteReaderAdapter.RouteTypeRule;
import net.osmand.binary.RouteDataObject; import net.osmand.binary.RouteDataObject;
@ -14,12 +15,15 @@ import net.osmand.plus.ApplicationMode;
import net.osmand.plus.OsmandApplication; import net.osmand.plus.OsmandApplication;
import net.osmand.plus.R; import net.osmand.plus.R;
import net.osmand.plus.routing.AlarmInfo.AlarmInfoType; import net.osmand.plus.routing.AlarmInfo.AlarmInfoType;
import net.osmand.router.ExitInfo;
import net.osmand.router.RouteSegmentResult; import net.osmand.router.RouteSegmentResult;
import net.osmand.router.RoutingContext; import net.osmand.router.RoutingContext;
import net.osmand.router.TurnType; import net.osmand.router.TurnType;
import net.osmand.util.Algorithms; import net.osmand.util.Algorithms;
import net.osmand.util.MapUtils; import net.osmand.util.MapUtils;
import org.apache.commons.logging.Log;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
import java.util.List; import java.util.List;
@ -27,6 +31,8 @@ import java.util.List;
import static net.osmand.binary.RouteDataObject.HEIGHT_UNDEFINED; import static net.osmand.binary.RouteDataObject.HEIGHT_UNDEFINED;
public class RouteCalculationResult { public class RouteCalculationResult {
private final static Log log = PlatformUtil.getLog(RouteCalculationResult.class);
private static double distanceClosestToIntermediate = 3000; private static double distanceClosestToIntermediate = 3000;
private static double distanceThresholdToIntermediate = 25; private static double distanceThresholdToIntermediate = 25;
// could not be null and immodifiable! // could not be null and immodifiable!
@ -318,15 +324,55 @@ public class RouteCalculationResult {
info.routeEndPointOffset = roundAboutEnd; info.routeEndPointOffset = roundAboutEnd;
} }
RouteSegmentResult next = list.get(lind); RouteSegmentResult next = list.get(lind);
info.setRef(next.getObject().getRef(ctx.getSettings().MAP_PREFERRED_LOCALE.get(), String ref = next.getObject().getRef(ctx.getSettings().MAP_PREFERRED_LOCALE.get(),
ctx.getSettings().MAP_TRANSLITERATE_NAMES.get(), next.isForwardDirection())); ctx.getSettings().MAP_TRANSLITERATE_NAMES.get(), next.isForwardDirection());
info.setRef(ref);
info.setStreetName(next.getObject().getName(ctx.getSettings().MAP_PREFERRED_LOCALE.get(), info.setStreetName(next.getObject().getName(ctx.getSettings().MAP_PREFERRED_LOCALE.get(),
ctx.getSettings().MAP_TRANSLITERATE_NAMES.get())); ctx.getSettings().MAP_TRANSLITERATE_NAMES.get()));
info.setDestinationName(next.getObject().getDestinationName(ctx.getSettings().MAP_PREFERRED_LOCALE.get(), info.setDestinationName(next.getObject().getDestinationName(ctx.getSettings().MAP_PREFERRED_LOCALE.get(),
ctx.getSettings().MAP_TRANSLITERATE_NAMES.get(), next.isForwardDirection())); ctx.getSettings().MAP_TRANSLITERATE_NAMES.get(), next.isForwardDirection()));
if (s.getObject().isExitPoint() && next.getObject().getHighway().equals("motorway_link")) {
ExitInfo exitInfo = new ExitInfo();
exitInfo.setRef(next.getObject().getExitRef());
exitInfo.setExitStreetName(next.getObject().getExitName());
info.setExitInfo(exitInfo);
}
if (ref != null) {
RouteDataObject nextRoad = next.getObject();
boolean isNextShieldFound = false;
int[] nextSegmentNameIds = nextRoad.nameIds;
for (int nm = 0; nm < nextSegmentNameIds.length; nm++) {
if (nextRoad.region.quickGetEncodingRule(nextSegmentNameIds[nm]).getTag().startsWith("road_ref")) {
info.setRouteDataObject(nextRoad);
isNextShieldFound = true;
}
}
if (!isNextShieldFound) {
for (int ind = lind; ind < list.size(); ind++) {
if (list.get(ind).getTurnType() != null) {
info.setRouteDataObject(null);
break;
} else {
RouteDataObject obj = list.get(ind).getObject();
int[] nameIds = obj.nameIds;
for (int idx = 0; idx < nameIds.length; idx ++) {
if (obj.region.routeEncodingRules.get(obj.nameIds[idx]).getTag().startsWith("road_ref")) {
info.setRouteDataObject(obj);
break;
}
}
if (info.getRouteDataObject() != null) {
break;
}
}
}
}
}
} }
String description = toString(turn, ctx, false) + " " + RoutingHelper.formatStreetName(info.getStreetName(), String description = toString(turn, ctx, false) + " " + RoutingHelper.formatStreetName(info.getStreetName(),
info.getRef(), info.getDestinationName(), ctx.getString(R.string.towards)); info.getRef(), info.getDestinationName(), ctx.getString(R.string.towards));
description = description.trim(); description = description.trim();
String[] pointNames = s.getObject().getPointNames(s.getStartPointIndex()); String[] pointNames = s.getObject().getPointNames(s.getStartPointIndex());

View file

@ -1,7 +1,11 @@
package net.osmand.plus.routing; package net.osmand.plus.routing;
import android.support.annotation.Nullable;
import net.osmand.binary.RouteDataObject;
import net.osmand.plus.OsmAndFormatter; import net.osmand.plus.OsmAndFormatter;
import net.osmand.plus.OsmandApplication; import net.osmand.plus.OsmandApplication;
import net.osmand.router.ExitInfo;
import net.osmand.router.TurnType; import net.osmand.router.TurnType;
public class RouteDirectionInfo { public class RouteDirectionInfo {
@ -22,6 +26,11 @@ public class RouteDirectionInfo {
private String destinationName; private String destinationName;
private RouteDataObject routeDataObject = null;
@Nullable
private ExitInfo exitInfo;
public String getDestinationName() { public String getDestinationName() {
return destinationName; return destinationName;
} }
@ -36,6 +45,14 @@ public class RouteDirectionInfo {
this.turnType = turnType; this.turnType = turnType;
} }
public RouteDataObject getRouteDataObject() {
return routeDataObject;
}
public void setRouteDataObject(RouteDataObject routeDataObject) {
this.routeDataObject = routeDataObject;
}
public String getDescriptionRoute(OsmandApplication ctx) { public String getDescriptionRoute(OsmandApplication ctx) {
if (!descriptionRoute.endsWith(OsmAndFormatter.getFormattedDistance(distance, ctx))) { if (!descriptionRoute.endsWith(OsmAndFormatter.getFormattedDistance(distance, ctx))) {
descriptionRoute += " " + OsmAndFormatter.getFormattedDistance(distance, ctx); descriptionRoute += " " + OsmAndFormatter.getFormattedDistance(distance, ctx);
@ -104,6 +121,15 @@ public class RouteDirectionInfo {
} }
public void setDistance(int distance) { public void setDistance(int distance) {
this.distance = distance; this.distance = distance;
}
@Nullable
public ExitInfo getExitInfo() {
return exitInfo;
}
public void setExitInfo(@Nullable ExitInfo exitInfo) {
this.exitInfo = exitInfo;
} }
} }

View file

@ -835,12 +835,12 @@ public class RoutingHelper {
if(n.distanceTo > 0 && n.directionInfo != null && !n.directionInfo.getTurnType().isSkipToSpeak() && if(n.distanceTo > 0 && n.directionInfo != null && !n.directionInfo.getTurnType().isSkipToSpeak() &&
voiceRouter.isDistanceLess(speed, n.distanceTo, voiceRouter.PREPARE_DISTANCE * 0.75f, 0f)) { voiceRouter.isDistanceLess(speed, n.distanceTo, voiceRouter.PREPARE_DISTANCE * 0.75f, 0f)) {
String nm = n.directionInfo.getStreetName(); String nm = n.directionInfo.getStreetName();
String rf = n.directionInfo.getRef(); // String rf = n.directionInfo.getRef();
String dn = n.directionInfo.getDestinationName(); String dn = n.directionInfo.getDestinationName();
if(next != null) { if(next != null) {
next[0] = n.directionInfo.getTurnType(); next[0] = n.directionInfo.getTurnType();
} }
return formatStreetName(nm, rf, dn, "»"); return formatStreetName(nm, null, dn, "»");
} }
RouteSegmentResult rs = getCurrentSegmentResult(); RouteSegmentResult rs = getCurrentSegmentResult();
if(rs != null) { if(rs != null) {
@ -864,10 +864,10 @@ public class RoutingHelper {
private String getRouteSegmentStreetName(RouteSegmentResult rs) { private String getRouteSegmentStreetName(RouteSegmentResult rs) {
String nm = rs.getObject().getName(settings.MAP_PREFERRED_LOCALE.get(), settings.MAP_TRANSLITERATE_NAMES.get()); String nm = rs.getObject().getName(settings.MAP_PREFERRED_LOCALE.get(), settings.MAP_TRANSLITERATE_NAMES.get());
String rf = rs.getObject().getRef(settings.MAP_PREFERRED_LOCALE.get(), settings.MAP_TRANSLITERATE_NAMES.get(), rs.isForwardDirection()); // String rf = rs.getObject().getRef(settings.MAP_PREFERRED_LOCALE.get(), settings.MAP_TRANSLITERATE_NAMES.get(), rs.isForwardDirection());
String dn = rs.getObject().getDestinationName(settings.MAP_PREFERRED_LOCALE.get(), String dn = rs.getObject().getDestinationName(settings.MAP_PREFERRED_LOCALE.get(),
settings.MAP_TRANSLITERATE_NAMES.get(), rs.isForwardDirection()); settings.MAP_TRANSLITERATE_NAMES.get(), rs.isForwardDirection());
return formatStreetName(nm, rf, dn, "»"); return formatStreetName(nm, null, dn, "»");
} }
public RouteSegmentResult getCurrentSegmentResult() { public RouteSegmentResult getCurrentSegmentResult() {

View file

@ -16,6 +16,7 @@ import net.osmand.plus.routing.data.StreetName;
import net.osmand.plus.voice.AbstractPrologCommandPlayer; import net.osmand.plus.voice.AbstractPrologCommandPlayer;
import net.osmand.plus.voice.CommandBuilder; import net.osmand.plus.voice.CommandBuilder;
import net.osmand.plus.voice.CommandPlayer; import net.osmand.plus.voice.CommandPlayer;
import net.osmand.router.ExitInfo;
import net.osmand.router.RouteSegmentResult; import net.osmand.router.RouteSegmentResult;
import net.osmand.router.TurnType; import net.osmand.router.TurnType;
import net.osmand.util.MapUtils; import net.osmand.util.MapUtils;
@ -618,13 +619,29 @@ public class VoiceRouter {
} }
} else { } else {
result.put("toRef", getNonNullString(getSpeakablePointName(i.getRef()))); result.put(TO_REF, getNonNullString(getSpeakablePointName(i.getRef())));
result.put(TO_STREET_NAME, getNonNullString(getSpeakablePointName(i.getStreetName()))); result.put(TO_STREET_NAME, getNonNullString(getSpeakablePointName(i.getStreetName())));
result.put(TO_DEST, ""); result.put(TO_DEST, "");
} }
return new StreetName(result); return new StreetName(result);
} }
private StreetName getSpeakableExitName(RouteDirectionInfo routeInfo, ExitInfo exitInfo, boolean includeDest) {
Map<String, String> result = new HashMap<>();
if (exitInfo == null || !router.getSettings().SPEAK_STREET_NAMES.get()) {
return new StreetName(result);
}
if (player != null && player.supportsStructuredStreetNames()) {
result.put(TO_REF, getNonNullString(getSpeakablePointName(exitInfo.getRef())));
result.put(TO_STREET_NAME, getNonNullString(getSpeakablePointName(exitInfo.getExitStreetName())));
result.put(TO_DEST, includeDest ? getNonNullString(getSpeakablePointName(routeInfo.getRef())) : "");
} else {
result.put(TO_REF, getNonNullString(getSpeakablePointName(exitInfo.getRef())));
result.put(TO_STREET_NAME, getNonNullString(getSpeakablePointName(exitInfo.getExitStreetName())));
result.put(TO_DEST, "");
}
return new StreetName(result);
}
private String getNonNullString(String speakablePointName) { private String getNonNullString(String speakablePointName) {
return speakablePointName == null ? "" : speakablePointName; return speakablePointName == null ? "" : speakablePointName;
@ -677,8 +694,14 @@ public class VoiceRouter {
if (p != null) { if (p != null) {
String tParam = getTurnType(next.getTurnType()); String tParam = getTurnType(next.getTurnType());
boolean isPlay = true; boolean isPlay = true;
ExitInfo exitInfo = next.getExitInfo();
String lang = player.getLanguage();
if (tParam != null) { if (tParam != null) {
p.turn(tParam, dist, getSpeakableStreetName(currentSegment, next, true)); if (exitInfo != null) {
p.takeExit(tParam, dist, getSpeakableExitName(next, exitInfo, true));
} else {
p.turn(tParam, dist, getSpeakableStreetName(currentSegment, next, true));
}
suppressDest = true; suppressDest = true;
} else if (next.getTurnType().isRoundAbout()) { } else if (next.getTurnType().isRoundAbout()) {
p.roundAbout(dist, next.getTurnType().getTurnAngle(), next.getTurnType().getExitOut(), getSpeakableStreetName(currentSegment, next, true)); p.roundAbout(dist, next.getTurnType().getTurnAngle(), next.getTurnType().getExitOut(), getSpeakableStreetName(currentSegment, next, true));
@ -744,9 +767,15 @@ public class VoiceRouter {
CommandBuilder p = getNewCommandPlayerToPlay(); CommandBuilder p = getNewCommandPlayerToPlay();
if (p != null) { if (p != null) {
String tParam = getTurnType(next.getTurnType()); String tParam = getTurnType(next.getTurnType());
ExitInfo exitInfo = next.getExitInfo();
boolean isplay = true; boolean isplay = true;
String lang = player.getLanguage();
if (tParam != null) { if (tParam != null) {
p.turn(tParam, getSpeakableStreetName(currentSegment, next, !suppressDest)); if (exitInfo != null) {
p.takeExit(tParam, getSpeakableExitName(next, exitInfo, !suppressDest));
} else {
p.turn(tParam, getSpeakableStreetName(currentSegment, next, !suppressDest));
}
} else if (next.getTurnType().isRoundAbout()) { } else if (next.getTurnType().isRoundAbout()) {
p.roundAbout(next.getTurnType().getTurnAngle(), next.getTurnType().getExitOut(), getSpeakableStreetName(currentSegment, next, !suppressDest)); p.roundAbout(next.getTurnType().getTurnAngle(), next.getTurnType().getExitOut(), getSpeakableStreetName(currentSegment, next, !suppressDest));
} else if (next.getTurnType().getValue() == TurnType.TU || next.getTurnType().getValue() == TurnType.TRU) { } else if (next.getTurnType().getValue() == TurnType.TU || next.getTurnType().getValue() == TurnType.TRU) {

View file

@ -1,13 +1,15 @@
package net.osmand.plus.views.mapwidgets; package net.osmand.plus.views.mapwidgets;
import android.animation.LayoutTransition;
import android.annotation.SuppressLint; import android.annotation.SuppressLint;
import android.app.Activity; import android.app.Activity;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.Typeface; import android.graphics.Typeface;
import android.graphics.drawable.Drawable; import android.graphics.drawable.Drawable;
import android.os.Build;
import android.os.Bundle; import android.os.Bundle;
import android.support.annotation.ColorInt; import android.support.annotation.ColorInt;
import android.support.annotation.ColorRes; import android.support.annotation.ColorRes;
@ -19,6 +21,7 @@ import android.support.v4.content.ContextCompat;
import android.support.v4.graphics.drawable.DrawableCompat; import android.support.v4.graphics.drawable.DrawableCompat;
import android.support.v7.widget.SwitchCompat; import android.support.v7.widget.SwitchCompat;
import android.text.ClipboardManager; import android.text.ClipboardManager;
import android.util.TypedValue;
import android.view.View; import android.view.View;
import android.view.View.OnClickListener; import android.view.View.OnClickListener;
import android.view.ViewGroup; import android.view.ViewGroup;
@ -34,6 +37,8 @@ import com.jwetherell.openmap.common.UTMPoint;
import net.osmand.AndroidUtils; import net.osmand.AndroidUtils;
import net.osmand.Location; import net.osmand.Location;
import net.osmand.LocationConvert; import net.osmand.LocationConvert;
import net.osmand.PlatformUtil;
import net.osmand.binary.BinaryMapRouteReaderAdapter;
import net.osmand.binary.RouteDataObject; import net.osmand.binary.RouteDataObject;
import net.osmand.data.LatLon; import net.osmand.data.LatLon;
import net.osmand.data.PointDescription; import net.osmand.data.PointDescription;
@ -52,8 +57,11 @@ import net.osmand.plus.helpers.AndroidUiHelper;
import net.osmand.plus.helpers.WaypointDialogHelper; import net.osmand.plus.helpers.WaypointDialogHelper;
import net.osmand.plus.helpers.WaypointHelper; import net.osmand.plus.helpers.WaypointHelper;
import net.osmand.plus.helpers.WaypointHelper.LocationPointWrapper; import net.osmand.plus.helpers.WaypointHelper.LocationPointWrapper;
import net.osmand.plus.render.OsmandRenderer;
import net.osmand.plus.render.TextRenderer;
import net.osmand.plus.routepreparationmenu.MapRouteInfoMenu; import net.osmand.plus.routepreparationmenu.MapRouteInfoMenu;
import net.osmand.plus.routepreparationmenu.ShowAlongTheRouteBottomSheet; import net.osmand.plus.routepreparationmenu.ShowAlongTheRouteBottomSheet;
import net.osmand.plus.routing.RouteCalculationResult;
import net.osmand.plus.routing.RouteDirectionInfo; import net.osmand.plus.routing.RouteDirectionInfo;
import net.osmand.plus.routing.RoutingHelper; import net.osmand.plus.routing.RoutingHelper;
import net.osmand.plus.views.OsmandMapLayer.DrawSettings; import net.osmand.plus.views.OsmandMapLayer.DrawSettings;
@ -61,10 +69,15 @@ import net.osmand.plus.views.OsmandMapTileView;
import net.osmand.plus.views.RulerControlLayer; import net.osmand.plus.views.RulerControlLayer;
import net.osmand.plus.views.mapwidgets.MapWidgetRegistry.WidgetState; import net.osmand.plus.views.mapwidgets.MapWidgetRegistry.WidgetState;
import net.osmand.plus.views.mapwidgets.NextTurnInfoWidget.TurnDrawable; import net.osmand.plus.views.mapwidgets.NextTurnInfoWidget.TurnDrawable;
import net.osmand.render.RenderingRuleSearchRequest;
import net.osmand.render.RenderingRulesStorage;
import net.osmand.router.ExitInfo;
import net.osmand.router.TurnType; import net.osmand.router.TurnType;
import net.osmand.util.Algorithms; import net.osmand.util.Algorithms;
import net.osmand.util.MapUtils; import net.osmand.util.MapUtils;
import org.apache.commons.logging.Log;
import java.util.Iterator; import java.util.Iterator;
import java.util.LinkedList; import java.util.LinkedList;
@ -903,6 +916,9 @@ public class MapInfoWidgetsFactory {
private View topBar; private View topBar;
private TextView addressText; private TextView addressText;
private TextView addressTextShadow; private TextView addressTextShadow;
private TextView exitRefText;
private ImageView shieldIcon;
private ImageView turnIcon;
private OsmAndLocationProvider locationProvider; private OsmAndLocationProvider locationProvider;
private WaypointHelper waypointHelper; private WaypointHelper waypointHelper;
private OsmandSettings settings; private OsmandSettings settings;
@ -911,12 +927,16 @@ public class MapInfoWidgetsFactory {
private TurnDrawable turnDrawable; private TurnDrawable turnDrawable;
private boolean showMarker; private boolean showMarker;
private int shadowRad; private int shadowRad;
private static final Log LOG = PlatformUtil.getLog(TopTextView.class);
public TopTextView(OsmandApplication app, MapActivity map) { public TopTextView(OsmandApplication app, MapActivity map) {
topBar = map.findViewById(R.id.map_top_bar); topBar = map.findViewById(R.id.map_top_bar);
addressText = (TextView) map.findViewById(R.id.map_address_text); addressText = (TextView) map.findViewById(R.id.map_address_text);
addressTextShadow = (TextView) map.findViewById(R.id.map_address_text_shadow); addressTextShadow = (TextView) map.findViewById(R.id.map_address_text_shadow);
waypointInfoBar = map.findViewById(R.id.waypoint_info_bar); waypointInfoBar = map.findViewById(R.id.waypoint_info_bar);
exitRefText = map.findViewById(R.id.map_exit_ref);
shieldIcon = map.findViewById(R.id.map_shield_icon);
turnIcon = map.findViewById(R.id.map_turn_icon);
this.routingHelper = app.getRoutingHelper(); this.routingHelper = app.getRoutingHelper();
locationProvider = app.getLocationProvider(); locationProvider = app.getLocationProvider();
this.map = map; this.map = map;
@ -940,6 +960,8 @@ public class MapInfoWidgetsFactory {
TextInfoWidget.updateTextColor((TextView) waypointInfoBar.findViewById(R.id.waypoint_text), TextInfoWidget.updateTextColor((TextView) waypointInfoBar.findViewById(R.id.waypoint_text),
(TextView) waypointInfoBar.findViewById(R.id.waypoint_text_shadow), (TextView) waypointInfoBar.findViewById(R.id.waypoint_text_shadow),
textColor, textShadowColor, bold, rad / 2); textColor, textShadowColor, bold, rad / 2);
exitRefText.setTextColor(nightMode ? map.getResources().getColor(R.color.text_color_primary_dark) :
map.getResources().getColor(R.color.color_white));
ImageView all = (ImageView) waypointInfoBar.findViewById(R.id.waypoint_more); ImageView all = (ImageView) waypointInfoBar.findViewById(R.id.waypoint_more);
ImageView remove = (ImageView) waypointInfoBar.findViewById(R.id.waypoint_close); ImageView remove = (ImageView) waypointInfoBar.findViewById(R.id.waypoint_close);
@ -955,6 +977,11 @@ public class MapInfoWidgetsFactory {
TurnType[] type = new TurnType[1]; TurnType[] type = new TurnType[1];
boolean showNextTurn = false; boolean showNextTurn = false;
boolean showMarker = this.showMarker; boolean showMarker = this.showMarker;
boolean showExitInfo = false;
boolean showShield = false;
ExitInfo exitInfo = null;
RouteDataObject object = null;
if (routingHelper != null && routingHelper.isRouteCalculated() && !routingHelper.isDeviatedFromRoute()) { if (routingHelper != null && routingHelper.isRouteCalculated() && !routingHelper.isDeviatedFromRoute()) {
if (routingHelper.isFollowingMode()) { if (routingHelper.isFollowingMode()) {
if (settings.SHOW_STREET_NAME.get()) { if (settings.SHOW_STREET_NAME.get()) {
@ -968,6 +995,25 @@ public class MapInfoWidgetsFactory {
turnDrawable.setColor(R.color.nav_arrow); turnDrawable.setColor(R.color.nav_arrow);
} }
} }
RouteCalculationResult.NextDirectionInfo nextDirInfo = routingHelper.getNextRouteDirectionInfo(
new RouteCalculationResult.NextDirectionInfo(), true);
RouteDirectionInfo directionInfo = nextDirInfo.directionInfo;
if (directionInfo != null && directionInfo.getExitInfo() != null) {
exitInfo = directionInfo.getExitInfo();
showExitInfo = true;
} else {
showExitInfo = false;
}
if (showExitInfo) {
text = exitInfo.getExitStreetName();
}
if (nextDirInfo.directionInfo.getRouteDataObject() != null) {
object = nextDirInfo.directionInfo.getRouteDataObject();
showShield = true;
}
} }
} else { } else {
int di = MapRouteInfoMenu.getDirectionInfo(); int di = MapRouteInfoMenu.getDirectionInfo();
@ -977,10 +1023,7 @@ public class MapInfoWidgetsFactory {
RouteDirectionInfo next = routingHelper.getRouteDirections().get(di); RouteDirectionInfo next = routingHelper.getRouteDirections().get(di);
type[0] = next.getTurnType(); type[0] = next.getTurnType();
turnDrawable.setColor(R.color.nav_arrow_distant); turnDrawable.setColor(R.color.nav_arrow_distant);
text = RoutingHelper.formatStreetName(next.getStreetName(), next.getRef(), next.getDestinationName(), "»"); text = RoutingHelper.formatStreetName(next.getStreetName(), null, next.getDestinationName(), "»");
// if (next.distance > 0) {
// text += " " + OsmAndFormatter.getFormattedDistance(next.distance, map.getMyApplication());
// }
if (text == null) { if (text == null) {
text = ""; text = "";
} }
@ -1029,25 +1072,37 @@ public class MapInfoWidgetsFactory {
AndroidUiHelper.updateVisibility(addressTextShadow, shadowRad > 0); AndroidUiHelper.updateVisibility(addressTextShadow, shadowRad > 0);
boolean update = turnDrawable.setTurnType(type[0]) || showMarker != this.showMarker; boolean update = turnDrawable.setTurnType(type[0]) || showMarker != this.showMarker;
this.showMarker = showMarker; this.showMarker = showMarker;
int h = addressText.getHeight() / 4 * 3; if (showShield) {
if (h != turnDrawable.getBounds().bottom) { if (setRoadShield(shieldIcon, object)) {
turnDrawable.setBounds(0, 0, h, h); AndroidUiHelper.updateVisibility(shieldIcon, true);
} else {
AndroidUiHelper.updateVisibility(shieldIcon, false);
}
} else {
AndroidUiHelper.updateVisibility(shieldIcon, false);
}
if (showExitInfo) {
String exitRef = exitInfo.getRef();
if (!Algorithms.isEmpty(exitRef)) {
exitRefText.setText(exitRef);
AndroidUiHelper.updateVisibility(exitRefText, true);
} else {
AndroidUiHelper.updateVisibility(exitRefText, false);
}
} else {
AndroidUiHelper.updateVisibility(exitRefText, false);
} }
if (update) { if (update) {
if (type[0] != null) { if (type[0] != null) {
addressTextShadow.setCompoundDrawables(turnDrawable, null, null, null); turnIcon.setImageDrawable(turnDrawable);
addressTextShadow.setCompoundDrawablePadding(4); AndroidUiHelper.updateVisibility(turnIcon, true);
addressText.setCompoundDrawables(turnDrawable, null, null, null);
addressText.setCompoundDrawablePadding(4);
} else if (showMarker) { } else if (showMarker) {
Drawable marker = map.getMyApplication().getUIUtilities().getIcon(R.drawable.ic_action_start_navigation, R.color.color_myloc_distance); Drawable marker = map.getMyApplication().getUIUtilities().getIcon(R.drawable.ic_action_start_navigation, R.color.color_myloc_distance);
addressTextShadow.setCompoundDrawablesWithIntrinsicBounds(marker, null, null, null); turnIcon.setImageDrawable(marker);
addressTextShadow.setCompoundDrawablePadding(4); AndroidUiHelper.updateVisibility(turnIcon, true);
addressText.setCompoundDrawablesWithIntrinsicBounds(marker, null, null, null);
addressText.setCompoundDrawablePadding(4);
} else { } else {
addressTextShadow.setCompoundDrawables(null, null, null, null); AndroidUiHelper.updateVisibility(turnIcon, false);
addressText.setCompoundDrawables(null, null, null, null);
} }
} }
if (!text.equals(addressText.getText().toString())) { if (!text.equals(addressText.getText().toString())) {
@ -1059,6 +1114,102 @@ public class MapInfoWidgetsFactory {
return false; return false;
} }
private boolean setRoadShield(ImageView view, RouteDataObject object) {
String nameTag = null;
String name = null;
StringBuilder additional = new StringBuilder();
for (int i = 0; i < object.nameIds.length; i++) {
String key = object.region.routeEncodingRules.get(object.nameIds[i]).getTag();
String val = object.names.get(object.nameIds[i]);
if (key.startsWith("road_ref")) {
nameTag = key;
name = val;
} else {
additional.append(key).append("=").append(val).append(";");
}
}
// LOG.debug("Additionals (names): " + additional.toString() );
Context context = topBar.getContext();
int[] tps = object.getTypes();
OsmandApplication app = ((OsmandApplication) context.getApplicationContext());
RenderingRulesStorage storage = app.getRendererRegistry().getCurrentSelectedRenderer();
boolean nightMode = app.getDaynightHelper().isNightMode();
RenderingRuleSearchRequest rreq = map.getMyApplication().getResourceManager()
.getRenderer().getSearchRequestWithAppliedCustomRules(storage, nightMode);
for (int i : tps) {
BinaryMapRouteReaderAdapter.RouteTypeRule tp = object.region.quickGetEncodingRule(i);
if (tp.getTag().equals("highway") || tp.getTag().equals("route")) {
rreq.setInitialTagValueZoom(tp.getTag(), tp.getValue(), 13, null);
} else {
additional.append(tp.getTag()).append("=").append(tp.getValue()).append(";");
}
}
rreq.setIntFilter(rreq.ALL.R_TEXT_LENGTH, name.length());
rreq.setStringFilter(rreq.ALL.R_NAME_TAG, nameTag);
rreq.setStringFilter(rreq.ALL.R_ADDITIONAL, additional.toString());
rreq.search(RenderingRulesStorage.TEXT_RULES);
OsmandRenderer.RenderingContext rc = new OsmandRenderer.RenderingContext(context);
TextRenderer textRenderer = new TextRenderer(context);
TextRenderer.TextDrawInfo text = new TextRenderer.TextDrawInfo(name);
Paint p = textRenderer.getPaintText();
p.setTypeface(Typeface.create("Droid Serif", Typeface.BOLD));
int shieldRes = -1;
if (rreq.isSpecified(rreq.ALL.R_TEXT_SHIELD)) {
text.setShieldResIcon(rreq.getStringPropertyValue(rreq.ALL.R_TEXT_SHIELD));
shieldRes = app.getResources().getIdentifier("h_"+text.getShieldResIcon(),
"drawable", app.getPackageName());
}
if (rreq.isSpecified(rreq.ALL.R_TEXT_COLOR)) {
p.setColor(rreq.getIntPropertyValue(rreq.ALL.R_TEXT_COLOR));
}
if (rreq.isSpecified(rreq.ALL.R_TEXT_SIZE)) {
float ts = rreq.getFloatPropertyValue(rreq.ALL.R_TEXT_SIZE);
textRenderer.getPaintText().setTextSize(
TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP, ts,
app.getResources().getDisplayMetrics()));
}
if (shieldRes != -1) {
float xSize;
float ySize;
Bitmap shield;
shield = BitmapFactory.decodeResource(app.getResources(), shieldRes);
ySize = shield.getHeight();
xSize = shield.getWidth();
float xyRatio = xSize/ySize;
//setting view propotions (height is fixed by toolbar size - 48dp);
int viewHeightPx = AndroidUtils.dpToPx(context, 48);
int viewWidthPx = (int) (viewHeightPx * xyRatio);
ViewGroup.LayoutParams params = view.getLayoutParams();
params.width = viewWidthPx;
view.setLayoutParams(params);
//creating bitmap according to size of resource
Bitmap bitmap = Bitmap.createBitmap((int) xSize, (int) ySize, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
text.fillProperties(rc, rreq, xSize/2, ySize/2 - p.getFontMetrics().ascent/2f);
textRenderer.drawShieldIcon(rc, canvas, text, text.getShieldResIcon());
textRenderer.drawWrappedText(canvas, text, 20);
view.setImageBitmap(bitmap);
return true;
}
return false;
}
public boolean updateWaypoint() { public boolean updateWaypoint() {
final LocationPointWrapper pnt = waypointHelper.getMostImportantLocationPoint(null); final LocationPointWrapper pnt = waypointHelper.getMostImportantLocationPoint(null);
boolean changed = this.lastPoint != pnt; boolean changed = this.lastPoint != pnt;

View file

@ -875,9 +875,11 @@ public class RouteInfoWidgetsFactory {
} }
private static class LanesDrawable extends Drawable { public static class LanesDrawable extends Drawable {
int[] lanes = null; public int[] lanes = null;
boolean imminent = false; boolean imminent = false;
public boolean isTurnByTurn = false;
public boolean isNightMode = false;
private Context ctx; private Context ctx;
private Paint paintBlack; private Paint paintBlack;
private Paint paintRouteDirection; private Paint paintRouteDirection;
@ -892,7 +894,7 @@ public class RouteInfoWidgetsFactory {
private int imgMinDelta; private int imgMinDelta;
private int imgMargin; private int imgMargin;
LanesDrawable(MapActivity ctx, float scaleCoefficent) { public LanesDrawable(MapActivity ctx, float scaleCoefficent) {
this.ctx = ctx; this.ctx = ctx;
OsmandSettings settings = ctx.getMyApplication().getSettings(); OsmandSettings settings = ctx.getMyApplication().getSettings();
leftSide = settings.DRIVING_REGION.get().leftHandDriving; leftSide = settings.DRIVING_REGION.get().leftHandDriving;
@ -916,7 +918,7 @@ public class RouteInfoWidgetsFactory {
paintSecondTurn.setColor(ctx.getResources().getColor(R.color.nav_arrow_distant)); paintSecondTurn.setColor(ctx.getResources().getColor(R.color.nav_arrow_distant));
} }
void updateBounds() { public void updateBounds() {
float w = 0; float w = 0;
float h = 0; float h = 0;
float delta = imgMinDelta; float delta = imgMinDelta;
@ -1031,8 +1033,13 @@ public class RouteInfoWidgetsFactory {
// canvas.translate((int) (16 * scaleCoefficient), 0); // canvas.translate((int) (16 * scaleCoefficient), 0);
for (int i = 0; i < lanes.length; i++) { for (int i = 0; i < lanes.length; i++) {
if ((lanes[i] & 1) == 1) { if ((lanes[i] & 1) == 1) {
paintRouteDirection.setColor(imminent ? ctx.getResources().getColor(R.color.nav_arrow_imminent) : if (isTurnByTurn){
ctx.getResources().getColor(R.color.nav_arrow)); paintRouteDirection.setColor(isNightMode ? ctx.getResources().getColor(R.color.active_color_primary_dark) :
ctx.getResources().getColor(R.color.active_color_primary_light));
} else {
paintRouteDirection.setColor(imminent ? ctx.getResources().getColor(R.color.nav_arrow_imminent) :
ctx.getResources().getColor(R.color.nav_arrow));
}
} else { } else {
paintRouteDirection.setColor(ctx.getResources().getColor(R.color.nav_arrow_distant)); paintRouteDirection.setColor(ctx.getResources().getColor(R.color.nav_arrow_distant));
} }

View file

@ -39,6 +39,7 @@ public class CommandBuilder {
protected static final String C_ATTENTION = "attention"; //$NON-NLS-1$ protected static final String C_ATTENTION = "attention"; //$NON-NLS-1$
protected static final String C_OFF_ROUTE = "off_route"; //$NON-NLS-1$ protected static final String C_OFF_ROUTE = "off_route"; //$NON-NLS-1$
protected static final String C_BACK_ON_ROUTE ="back_on_route"; //$NON-NLS-1$ protected static final String C_BACK_ON_ROUTE ="back_on_route"; //$NON-NLS-1$
protected static final String C_TAKE_EXIT = "take_exit"; //$NON-NLS-1$
protected static final String C_BEAR_LEFT = "bear_left"; //$NON-NLS-1$ protected static final String C_BEAR_LEFT = "bear_left"; //$NON-NLS-1$
@ -178,6 +179,14 @@ public class CommandBuilder {
return alt(prepareStruct(C_TURN, param, dist, streetName), prepareStruct(C_TURN, param, dist)); return alt(prepareStruct(C_TURN, param, dist, streetName), prepareStruct(C_TURN, param, dist));
} }
public CommandBuilder takeExit(String turnType, StreetName streetName) {
return alt(prepareStruct(C_TAKE_EXIT, turnType, streetName), prepareStruct(C_TAKE_EXIT, turnType));
}
public CommandBuilder takeExit(String turnType, double dist, StreetName streetName) {
return alt(prepareStruct(C_TAKE_EXIT, turnType, dist, streetName), prepareStruct(C_TAKE_EXIT, turnType, dist));
}
/** /**
* *
* @param param A_LEFT, A_RIGHT, ... * @param param A_LEFT, A_RIGHT, ...

View file

@ -115,6 +115,14 @@ public class JSCommandBuilder extends CommandBuilder {
return addCommand(C_TURN, param, dist, convertStreetName(streetName)); return addCommand(C_TURN, param, dist, convertStreetName(streetName));
} }
public JSCommandBuilder takeExit(String turnType, StreetName streetName) {
return takeExit(turnType, -1, streetName);
}
public JSCommandBuilder takeExit(String turnType, double dist, StreetName streetName) {
return addCommand(C_TAKE_EXIT, turnType, dist, convertStreetName(streetName));
}
/** /**
* *
* @param param A_LEFT, A_RIGHT, ... * @param param A_LEFT, A_RIGHT, ...