Compare commits

...

5 Commits

Author SHA1 Message Date
Harry Bond
c287dde93f Merge remote-tracking branch 'origin/yannikbloscheck-greenery' into test/2025.07.10
# Conflicts:
#    data/drules_proto.bin
#    data/drules_proto_default_dark.bin
#    data/drules_proto_default_light.bin
#    data/drules_proto_outdoors_dark.bin
#    data/drules_proto_outdoors_light.bin


Signed-off-by: Harry Bond <me@hbond.xyz>
2025-07-10 21:47:23 +01:00
Harry Bond
f7e4fdad6a [Android] Add current opening hours status to placepage preview
And refresh it every 45s

Signed-off-by: Harry Bond <me@hbond.xyz>


Signed-off-by: Harry Bond <me@hbond.xyz>

Signed-off-by: Harry Bond <me@hbond.xyz>

Signed-off-by: Harry Bond <me@hbond.xyz>

Signed-off-by: Harry Bond <me@hbond.xyz>

Signed-off-by: Harry Bond <me@hbond.xyz>

Signed-off-by: Harry Bond <me@hbond.xyz>

Signed-off-by: Harry Bond <me@hbond.xyz>

Signed-off-by: Harry Bond <me@hbond.xyz>
2025-07-10 19:41:51 +01:00
Harry Bond
f59fb509c9 [core] Remove legacy opening_hours stuff
Signed-off-by: Harry Bond <me@hbond.xyz>
2025-07-10 19:41:50 +01:00
Yannik Bloscheck
fae8849869 [styles] Regenerated files for changed how the greenery system works
Signed-off-by: Yannik Bloscheck <git@yannikbloscheck.com>
2025-07-05 10:18:15 +02:00
Yannik Bloscheck
3585bd4fad [styles] Changed how the greenery system works
Signed-off-by: Yannik Bloscheck <git@yannikbloscheck.com>
2025-07-05 10:17:11 +02:00
24 changed files with 2151 additions and 2229 deletions

View File

@@ -321,4 +321,30 @@ Java_app_organicmaps_editor_OpeningHours_nativeIsTimetableStringValid(JNIEnv * e
{
return OpeningHours(jni::ToNativeString(env, jSource)).IsValid();
}
JNIEXPORT jobject JNICALL
Java_app_organicmaps_editor_OpeningHours_nativeCurrentState(JNIEnv * env, jclass clazz, jobjectArray jTts)
{
TimeTableSet tts = NativeTimetableSet(env, jTts);
time_t const now = time(nullptr);
/// @todo We should check closed/open time for specific feature's timezone.
OpeningHours::InfoT ohInfo = MakeOpeningHours(tts).GetInfo(now);
jclass ohStateClass = jni::GetGlobalClassRef(env, "app/organicmaps/editor/OhState");
jclass ruleStateClass = jni::GetGlobalClassRef(env, "app/organicmaps/editor/OhState$State");
static const std::unordered_map<RuleState, const char*> ruleState = {
{RuleState::Open, "Open"},
{RuleState::Closed, "Closed"},
{RuleState::Unknown, "Unknown"}
};
jfieldID stateField = env->GetStaticFieldID(ruleStateClass, ruleState.at(ohInfo.state), "Lapp/organicmaps/editor/OhState$State;");
jobject stateObj = env->GetStaticObjectField(ruleStateClass, stateField);
jmethodID constructor = env->GetMethodID(ohStateClass, "<init>", "(Lapp/organicmaps/editor/OhState$State;JJ)V");
jobject javaOhState = env->NewObject(ohStateClass, constructor, stateObj, (jlong) ohInfo.nextTimeOpen, (jlong) ohInfo.nextTimeClosed);
return javaOhState;
}
} // extern "C"

View File

@@ -0,0 +1,30 @@
package app.organicmaps.editor;
import androidx.annotation.Keep;
// Used by JNI.
@Keep
public class OhState
{
public enum State
{
Open,
Closed,
Unknown
}
public State state;
/** Unix timestamp in seconds**/
public long nextTimeOpen;
/** Unix timestamp in seconds **/
public long nextTimeClosed;
// Used by JNI.
@Keep
public OhState(State state, long nextTimeOpen, long nextTimeClosed)
{
this.state = state;
this.nextTimeOpen = nextTimeOpen;
this.nextTimeClosed = nextTimeClosed;
}
}

View File

@@ -60,4 +60,6 @@ public final class OpeningHours
* @return true if timetable string is valid OSM timetable.
*/
public static native boolean nativeIsTimetableStringValid(String source);
public static native OhState nativeCurrentState(@NonNull Timetable[] timetables);
}

View File

@@ -33,11 +33,16 @@ import app.organicmaps.downloader.CountryItem;
import app.organicmaps.downloader.DownloaderStatusIcon;
import app.organicmaps.downloader.MapManager;
import app.organicmaps.editor.Editor;
import app.organicmaps.editor.OhState;
import app.organicmaps.editor.OpeningHours;
import app.organicmaps.editor.data.HoursMinutes;
import app.organicmaps.editor.data.Timetable;
import app.organicmaps.location.LocationHelper;
import app.organicmaps.location.LocationListener;
import app.organicmaps.location.SensorHelper;
import app.organicmaps.location.SensorListener;
import app.organicmaps.routing.RoutingController;
import app.organicmaps.util.DateUtils;
import app.organicmaps.util.SharingUtils;
import app.organicmaps.util.StringUtils;
import app.organicmaps.util.UiUtils;
@@ -54,6 +59,9 @@ import com.google.android.material.appbar.MaterialToolbar;
import com.google.android.material.button.MaterialButton;
import com.google.android.material.textview.MaterialTextView;
import java.time.Instant;
import java.time.ZoneId;
import java.time.ZonedDateTime;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
@@ -83,12 +91,15 @@ public class PlacePageView extends Fragment implements View.OnClickListener,
CoordinatesFormat.MGRS,
CoordinatesFormat.OSMLink);
private View mFrame;
private Context mContext;
// Preview.
private ViewGroup mPreview;
private MaterialToolbar mToolbar;
private MaterialTextView mTvTitle;
private MaterialTextView mTvSecondaryTitle;
private MaterialTextView mTvSubtitle;
private MaterialTextView mTvOpenState;
private ArrowView mAvDirection;
private MaterialTextView mTvDistance;
private MaterialTextView mTvAddress;
@@ -201,7 +212,6 @@ public class PlacePageView extends Fragment implements View.OnClickListener,
mFrame = view;
mFrame.setOnClickListener((v) -> mPlacePageViewListener.onPlacePageRequestToggleState());
mPreview = mFrame.findViewById(R.id.pp__preview);
mFrame.addOnLayoutChangeListener((v, left, top, right, bottom, oldLeft, oldTop, oldRight, oldBottom) -> {
@@ -220,6 +230,7 @@ public class PlacePageView extends Fragment implements View.OnClickListener,
mTvSecondaryTitle.setOnClickListener(this);
mToolbar = mFrame.findViewById(R.id.toolbar);
mTvSubtitle = mPreview.findViewById(R.id.tv__subtitle);
mTvOpenState = mPreview.findViewById(R.id.tv__open_state);
View directionFrame = mPreview.findViewById(R.id.direction_frame);
mTvDistance = mPreview.findViewById(R.id.tv__straight_distance);
@@ -312,6 +323,7 @@ public class PlacePageView extends Fragment implements View.OnClickListener,
mViewModel.getMapObject().removeObserver(this);
LocationHelper.from(requireContext()).removeListener(this);
SensorHelper.from(requireContext()).removeListener(this);
UiThread.cancelDelayedTasks(updateOpenState);
detachCountry();
}
@@ -412,6 +424,8 @@ public class PlacePageView extends Fragment implements View.OnClickListener,
{
UiUtils.setTextAndHideIfEmpty(mTvTitle, mMapObject.getTitle());
UiUtils.setTextAndHideIfEmpty(mTvSecondaryTitle, mMapObject.getSecondaryTitle());
refreshOpenState();
if (mToolbar != null)
mToolbar.setTitle(mMapObject.getTitle());
setTextAndColorizeSubtitle();
@@ -546,6 +560,62 @@ public class PlacePageView extends Fragment implements View.OnClickListener,
mTvLatlon.setText(latLon);
}
Runnable updateOpenState = this::refreshOpenState;
private void refreshOpenState()
{
UiThread.runLater(updateOpenState, 45000); // Refresh every 45s
final String ohStr = mMapObject.getMetadata(Metadata.MetadataType.FMD_OPEN_HOURS);
final Timetable[] timetables = OpeningHours.nativeTimetablesFromString(ohStr);
if (timetables != null && timetables.length != 0)
{
final Context context = requireContext();
final OhState poiState = OpeningHours.nativeCurrentState(timetables);
// Ignore unknown rule state
if (poiState.state == OhState.State.Unknown)
{ UiUtils.hide(mTvOpenState); return; }
// Get colours
final ForegroundColorSpan colorGreen = new ForegroundColorSpan(ContextCompat.getColor(context, R.color.base_green));
final ForegroundColorSpan colorYellow = new ForegroundColorSpan(ContextCompat.getColor(context, R.color.base_yellow));
final ForegroundColorSpan colorRed = new ForegroundColorSpan(ContextCompat.getColor(context, R.color.base_red));
// Get next state info
final SpannableStringBuilder openStateString = new SpannableStringBuilder();
final boolean isOpen = (poiState.state == OhState.State.Open); // False == Closed due to early exit for Unknown
final long nextStateTime = isOpen ? poiState.nextTimeClosed : poiState.nextTimeOpen; // Unix time (seconds)
final int minsToNextState = (int) ((nextStateTime - (System.currentTimeMillis() / 1000)) / 60);
if (minsToNextState <= 60) // POI opens/closes in 60 mins
{
final String minsToChangeStr = minsToNextState + " " + getString(R.string.minute);
final String nextChangeFormatted = getString(isOpen ? R.string.closes_in : R.string.opens_in, minsToChangeStr);
final ForegroundColorSpan nextChangeColor = isOpen ? colorYellow : colorRed;
//TODO: We should check closed/open time for specific feature's timezone.
ZonedDateTime time = ZonedDateTime.ofInstant(Instant.ofEpochSecond(nextStateTime), ZoneId.systemDefault());
String localizedTime = new HoursMinutes(time.getHour(), time.getMinute(), DateUtils.is24HourFormat(context)).toString();
openStateString.append(nextChangeFormatted, nextChangeColor, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE)
.append("") // Add spacer
.append(getString(R.string.at, localizedTime));
}
else if (isOpen)
openStateString.append(getString(R.string.open_now), colorGreen, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
//TODO: Add "Closes at 18:00" etc
else // Closed
openStateString.append(getString(R.string.closed_now), colorRed, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
//TODO: Add "Opens at 18:00" etc
UiUtils.setTextAndHideIfEmpty(mTvOpenState, openStateString);
return;
}
// No valid timetable
UiUtils.hide(mTvOpenState);
}
private void addOrganisation()
{
((MwmActivity) requireActivity()).showPositionChooserForEditor(true, false);
@@ -556,9 +626,6 @@ public class PlacePageView extends Fragment implements View.OnClickListener,
((MwmActivity) requireActivity()).showPositionChooserForEditor(false, true);
}
/// @todo
/// - Why ll__place_editor and ll__place_latlon check if (mMapObject == null)
@Override
public void onClick(View v)
{

View File

@@ -71,6 +71,16 @@
android:textAppearance="@style/MwmTextAppearance.Body3"
tools:background="#300000F0"
tools:text="Subtitle, very very very very very very very long" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/tv__open_state"
android:textAlignment="viewStart"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/margin_quarter"
android:ellipsize="end"
android:textAppearance="@style/MwmTextAppearance.Body3"
tools:background="#300000F0"
tools:text="Open • Closing in 45 min" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/tv__address"
android:textAlignment="viewStart"

View File

@@ -967,4 +967,7 @@
<string name="ruler">Ruler</string>
<string name="bookmark_color">Bookmark color</string>
<string name="about_help">About &amp; Help</string>
<string name="open_now">Open now</string>
<string name="closed_now">Closed now</string>
<string name="at">at %s</string>
</resources>

View File

@@ -22,22 +22,20 @@
328965
352205
394752
401446
462602
593674
854541
855309
929809
988160
990018
1118464
1118481
1184274
1251584
1272880
1317888
1359565
1381632
1449728
1642503
1643545
1643785
@@ -146,7 +144,6 @@
6164237
6173981
6247213
6272197
6291544
6381914
6381921
@@ -220,52 +217,69 @@
10426903
10592406
10790054
10796367
11053224
11057133
11058780
11058773
11112295
11184810
11250586
11387999
11321948
11579812
11585379
11650146
11650917
11711154
11716458
11720246
11720952
11770767
11836942
11841150
11846761
11848043
11898395
11979115
12000284
12039862
12105912
12110705
12373110
12504182
12517551
12837073
12895428
12898689
13030021
13031851
13161612
13163437
13227146
13229526
13407549
13420474
13424014
13538264
13555607
13621402
13685196
13818270
13947850
13949600
13952918
14013333
14014162
14015375
14079128
14081171
14209512
14210459
14212247
14212502
14275263
14409117
14560552
14802147
14806505
14933676
14934482
14951168
14999725
15001506
15014691
15022389
@@ -281,9 +295,12 @@
15263939
15265772
15524822
15590858
15590859
15592411
15592899
15656370
15656651
15658734
15690752
15754290
@@ -338,10 +355,12 @@
16776442
16776958
16777215
218112546
221978645
222898459
223036995
223300167
227203303
233867264
234004016
234880250
@@ -377,11 +396,9 @@
452984831
609045837
654706176
655629312
658186261
659106075
659244611
666290539
670074880
670211632
670398976
@@ -453,10 +470,10 @@
1090519039
1216522952
1291845632
1291854370
1291855390
1292174597
1292240384
1292247078
1292700173
1292700941
1292964096
@@ -498,7 +515,6 @@
1297898588
1298019613
1298092845
1298117829
1298131758
1298227553
1298283903
@@ -512,6 +528,7 @@
1300267136
1300332657
1300793480
1300945127
1300990719
1301043238
1301056384
@@ -561,7 +578,6 @@
1711276032
1711670784
1711677478
1712264192
1713184029
1714046273
1714104359
@@ -595,16 +611,15 @@
1721782290
1724152575
1724368575
1724437644
1725290194
1727174424
1728053247
1931024665
1943327690
2147483648
2147492386
2147812613
2147878400
2147885094
2148141581
2148214779
2149069336
@@ -622,7 +637,6 @@
2152615485
2153076053
2153536593
2153755845
2153769774
2153921919
2153997148
@@ -632,6 +646,7 @@
2155839359
2155905152
2156431496
2156583143
2156681254
2156694400
2157291602
@@ -654,7 +669,6 @@
2566914048
2567571981
2567645179
2567902208
2568240148
2568499736
2568822045
@@ -675,7 +689,6 @@
2576782726
2579790591
2580006591
2580075660
2582553856
2583432731
2583691006

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

File diff suppressed because it is too large Load Diff

View File

@@ -41,7 +41,6 @@
@glacier: #111111;
@water: #002222;
@water_bad: #00261e;
@river: #062026;
@wetland: #001919;
@beach: #28281A;
@barerock: #302A2A;
@@ -50,17 +49,38 @@
/*3.2 Vegetation*/
@forest: #141C00;
@heath: #0F1400;
@green0: #0F1400;
@green1: #131900;
@green1b: #141C00;
@green2: #141C00;
@green3: #141C00;
@green4: #141C00;
@green5: #141C00;
@green6: #2F4000;
@residential_garden: #000000;
@residential_garden_13: #000000;
@residential_garden_12: #000000;
@park: #000000;
@park_13: #000000;
@park_12: #000000;
@park_11: #000000;
@park_10: #000000;
@heath: #141C00;
@heath_13: #141C00;
@heath_12: #141C00;
@heath_11: #141C00;
@grass: #141C00;
@grass_13: #141C00;
@grass_12: #141C00;
@grass_11: #141C00;
@flowers: #141C00;
@allotments: #141C00;
@allotments_13: #141C00;
@allotments_12: #141C00;
@scrubs: #141C00;
@scrubs_13: #141C00;
@scrubs_12: #141C00;
@scrubs_11: #141C00;
@woods: #161F00;
@woods_13: #161F00;
@woods_12: #161F00;
@woods_11: #161F00;
@woods_10: #161F00;
@protected_nature: #2F4000;
/* 4.LANDUSE */
/*4.1 Main landuse*/

View File

@@ -115,81 +115,108 @@ area|z14-[leisure=miniature_golf],
area|z16-[landuse=flowerbed],
{fill-opacity: 1;}
area|z10-12[leisure=park],
{fill-color: @green0;}
area|z13-15[leisure=park],
{fill-color: @green1;}
area|z14-15[natural=scrub],
{fill-color: @green1;}
area|z16-[leisure=park],
{fill-color: @green2;}
area|z16-[natural=scrub],
{fill-color: @green3;}
area|z10[leisure=park],
{fill-color: @park_10;}
area|z11[leisure=park],
{fill-color: @park_11;}
area|z12[leisure=park],
{fill-color: @park_12;}
area|z13[leisure=park],
{fill-color: @park_13;}
area|z14-[leisure=park],
{fill-color: @park;}
area|z11[natural=heath],
{fill-color: @heath_11;}
area|z12[natural=heath],
{fill-color: @heath_12;}
area|z13[natural=heath],
{fill-color: @heath_13;}
area|z14-[natural=heath],
{fill-color: @heath;}
area|z11[landuse=grass],
area|z11[natural=grassland],
area|z11[landuse=meadow],
{fill-color: @grass_11;}
area|z12[landuse=grass],
area|z12[natural=grassland],
area|z12[leisure=golf_course],
area|z12[landuse=meadow],
area|z12[landuse=recreation_ground],
area|z12[landuse=village_green],
{fill-color: @grass_12;}
area|z13[landuse=grass],
area|z13[natural=grassland],
area|z13[leisure=golf_course],
area|z13[landuse=meadow],
area|z13[landuse=recreation_ground],
area|z13[landuse=village_green],
{fill-color: @grass_13;}
area|z14-[landuse=grass],
area|z14-[natural=grassland],
area|z14-[leisure=golf_course],
area|z14-[landuse=meadow],
area|z14-[landuse=recreation_ground],
area|z14-[landuse=village_green],
area|z14-[leisure=miniature_golf],
{fill-color: @grass;}
area|z16-[landuse=flowerbed],
{fill-color: @flowers;}
area|z14-15[landuse=grass],
{fill-color: @green0;}
area|z10[landuse=forest],
area|z16-[landuse=grass],
area|z14-15[natural=grassland],
area|z14-[leisure=golf_course],
area|z14-[leisure=miniature_golf],
area|z12[leisure=garden],
area|z12[landuse=allotments],
area|z12[landuse=orchard],
area|z12[landuse=plant_nursery],
area|z12[landuse=vineyard],
{fill-color: @allotments_12;}
area|z13[leisure=garden],
area|z13[landuse=allotments],
area|z13[landuse=orchard],
area|z13[landuse=plant_nursery],
area|z13[landuse=vineyard],
{fill-color: @allotments_13;}
area|z14-[leisure=garden],
area|z14-[landuse=allotments],
area|z14-[landuse=orchard],
area|z14-[landuse=plant_nursery],
area|z14-[landuse=vineyard],
area|z14-15[landuse=meadow],
area|z14-[landuse=recreation_ground],
area|z14-[landuse=village_green],
{fill-color: @green1;}
{fill-color: @allotments;}
area|z12[leisure=garden][garden:type=residential],
{fill-color: @residential_garden_12;}
area|z13[leisure=garden][garden:type=residential],
{fill-color: @residential_garden_13;}
area|z14-[leisure=garden][garden:type=residential],
{fill-color: @residential_garden;}
area|z11[natural=scrub],
{fill-color: @scrubs_11;}
area|z12[natural=scrub],
{fill-color: @scrubs_12;}
area|z13[natural=scrub],
{fill-color: @scrubs_13;}
area|z14-[natural=scrub],
{fill-color: @scrubs;}
area|z10[landuse=forest],
{fill-color: @woods_10;}
area|z11[landuse=forest],
area|z16-[natural=grassland],
area|z16-[landuse=meadow],
{fill-color: @green1b;}
{fill-color: @woods_11;}
area|z12[landuse=forest],
area|z12[leisure=garden],
{fill-color: @green2;}
{fill-color: @woods_12;}
area|z13[landuse=forest],
area|z13[leisure=garden],
{fill-color: @green3;}
area|z14[landuse=forest],
area|z14[leisure=garden],
{fill-color: @green4;}
area|z15[landuse=forest],
area|z15[leisure=garden],
{fill-color: @green5;}
area|z16-[landuse=forest],
area|z16-[leisure=garden],
{fill-color: @forest;}
{fill-color: @woods_13;}
area|z14-[landuse=forest],
{fill-color: @woods;}
area|z12-[leisure=garden][garden:type=residential],
{fill-color: @green0;}
area|z16-[leisure=garden][garden:type=residential],
{fill-color: @green1;}
area|z17-[leisure=garden][garden:type=residential],
{fill-color: @green2;}
area|z11-[natural=heath],
{fill-color: @heath;}
area|z11-13[landuse=grass],
area|z11-13[natural=grassland],
area|z12-13[leisure=golf_course],
area|z12-13[landuse=allotments],
area|z12-13[landuse=orchard],
area|z12-13[landuse=plant_nursery],
area|z12-13[landuse=vineyard],
area|z11-13[landuse=meadow],
area|z12-13[landuse=recreation_ground],
area|z12-13[landuse=village_green],
area|z11-13[natural=scrub],
{fill-color: @green0;}
/* Next types are hardcoded to have a hatching-style fill, see drape_frontend/stylist.cpp */
area|z10-17[leisure=nature_reserve],
area|z10-17[boundary=national_park],
area|z10-17[boundary=protected_area][protect_class=1],
{fill-opacity: 0.2; fill-color: @green6;}
{fill-opacity: 0.2; fill-color: @protected_nature;}
area|z10-16[boundary=aboriginal_lands],
{fill-opacity: 0.07; fill-color: @indigenous_lands;}
@@ -250,7 +277,7 @@ line|z13-[waterway=stream],
line|z13-[waterway=canal],
line|z13-[waterway=fish_pass],
line|z13-[natural=strait],
{opacity: 0.7; color: @river;}
{opacity: 0.95; color: @water;}
/* 6.1 Area water(lake,pond etc.) */
@@ -280,47 +307,47 @@ area|z11-[natural=wetland]
/* 6.2 Line water(river,canal etc.) */
line|z10[waterway=river],
{width: 1;}
line|z11-12[waterway=river],
{width: 1.2;}
line|z11-12[waterway=river],
{width: 1.4;}
line|z13[waterway=river],
{width: 1.6;}
{width: 1.7;}
line|z13[waterway=stream],
line|z13[waterway=canal],
line|z13[waterway=fish_pass],
line|z13[natural=strait],
{width: 0.7;}
{width: 0.9;}
line|z13[waterway=stream][intermittent=yes]
{width: 0.7;dashes: 2.7,2.7;}
{width: 0.9;dashes: 2.7,2.7;}
line|z14[waterway=river],
{width: 1.8;}
{width: 2.0;}
line|z14[waterway=stream],
line|z14[waterway=canal],
line|z14[waterway=fish_pass],
line|z14[natural=strait],
{width: 1;}
{width: 1.2;}
line|z14[waterway=stream][intermittent=yes]
{width: 1;dashes: 2.7,2.7;}
{width: 1.2;dashes: 2.7,2.7;}
line|z15-[waterway=river],
{width: 2.2;}
{width: 2.4;}
line|z15-[waterway=stream],
line|z15-[waterway=canal],
line|z15-[waterway=fish_pass],
line|z15-[natural=strait],
{width: 1.6;}
{width: 1.8;}
line|z15-[waterway=stream][intermittent=yes]
{width: 1.4;dashes: 4.95,4.95;}
{width: 1.6;dashes: 4.95,4.95;}
node|z16-[waterway=lock_gate],
{icon-image: dot-m.svg;}
line|z13-[waterway=ditch],
line|z13-[waterway=drain],
{opacity: 0.7; color: @water_bad; width: 1.5; dashes: 2.7,2.7;}
{opacity: 0.7; color: @water_bad; width: 1.7; dashes: 2.7,2.7;}
line|z16-[waterway=ditch],
line|z16-[waterway=drain],
{width: 3;}
@@ -399,17 +426,9 @@ area|z14-[piste:type=snow_park],
/* 7.4 Cemetery */
area|z14[landuse=cemetery],
area|z14[amenity=grave_yard]
{fill-color: @green2;fill-opacity: 0.85;}
area|z15-[amenity=grave_yard],
area|z15-[landuse=cemetery]
{fill-color: @green2;}
area|z16-[amenity=grave_yard],
area|z16-[landuse=cemetery]
{fill-color: @green3;}
area|z14-[landuse=cemetery],
area|z14-[amenity=grave_yard]
{fill-color: @flowers;}
/* 7.5 Pedestrian areas */
@@ -562,7 +581,7 @@ line|z19-[waterway=weir],
{width: 8;}
line|z14-[man_made=cutline],
{width: 1;color: @green0; opacity: 0.4;}
{width: 1;color: @grass;}
line|z15[man_made=cutline],
{width: 1.5;}
line|z16[man_made=cutline],

View File

@@ -41,7 +41,6 @@
@glacier: #FFFFFF;
@water: #8AD8E7;
@water_bad: #95C5B8;
@river: #5FB4C5;
@wetland: #C3E0D1;
@beach: #FADDA0;
@barerock: #D9D2BF;
@@ -50,17 +49,37 @@
/*3.2 Vegetation*/
@residential_garden: #EDE5CA;
@residential_garden_13: #EDE5CB;
@residential_garden_12: #EEE6CB;
@park: #D5DB8F;
@park_13: #D6DC93;
@park_12: #D8DD96;
@park_11: #D8DC97;
@park_10: #DBDD9D;
@heath: #CED797;
@green0: #C8D48C;
@green1: #C4D181;
@green1b: #BECC76;
@green2: #B6C96B;
@green3: #B0C763;
@green4: #B2C76A;
@green5: #ADC45F;
@forest: #A8BE5C;
@green6: #7B8F35;
@flowers: #B6C96B;
@heath_13: #CFD89A;
@heath_12: #D2D99E;
@heath_11: #D4DAA0;
@grass: #C4D181;
@grass_13: #C6D285;
@grass_12: #C9D48A;
@grass_11: #CCD58E;
@flowers: #BECC76;
@allotments: #D5D395;
@allotments_13: #D6D498;
@allotments_12: #D8D59B;
@scrubs: #B1C765;
@scrubs_13: #B4C96B;
@scrubs_12: #B8CB71;
@scrubs_11: #BCCC76;
@woods: #A4BD4F;
@woods_13: #A8BE55;
@woods_12: #ACC25C;
@woods_11: #B1C462;
@woods_10: #B4C469;
@protected_nature: #7B8F35;
/* 4.LANDUSE */
/*4.1 Main landuse*/
@@ -79,7 +98,7 @@
@parking: #E8EFEC;
@military: #DE2D28;
@prison: #727272;
@farmland: #E4E0AD;
@farmland: #E3DEAC;
@farmyard: #E6D6AF;
/*4.2 Aerodrome*/

View File

@@ -11,7 +11,7 @@ line|z12-[waterway=stream],
line|z13-[waterway=fish_pass],
line|z15-[waterway=ditch],
line|z15-[waterway=drain],
{opacity: 1; color: @river;}
{opacity: 1; color: @water;}
/* 6.2 Line water(river,canal etc.) */
@@ -74,7 +74,7 @@ line[waterway][tunnel]
line|z13-[man_made=cutline],
{width: 1.7; color: @green0; opacity: 0.6;}
{width: 1.7; color: @grass;}
line|z14[man_made=cutline],
{width: 2.2;}
line|z15[man_made=cutline],

View File

@@ -16,7 +16,6 @@ set(SRC
power_manager_tests.cpp
search_api_tests.cpp
transliteration_test.cpp
working_time_tests.cpp
elevation_info_tests.cpp
track_statistics_tests.cpp
)

View File

@@ -1,62 +0,0 @@
#include "testing/testing.hpp"
#include "map/osm_opening_hours.hpp"
using namespace osm;
UNIT_TEST(WorkingTime_OpenSoon)
{
// 1-jan-2000 08:50
std::tm when = {};
when.tm_mday = 1;
when.tm_mon = 0;
when.tm_year = 100;
when.tm_hour = 8;
when.tm_min = 50;
time_t now = std::mktime(&when);
TEST_EQUAL(PlaceStateCheck("09:00-21:00", now), EPlaceState::OpenSoon, ());
}
UNIT_TEST(WorkingTime_CloseSoon)
{
// 1-jan-2000 20:50
std::tm when = {};
when.tm_mday = 1;
when.tm_mon = 0;
when.tm_year = 100;
when.tm_hour = 20;
when.tm_min = 50;
time_t now = std::mktime(&when);
TEST_EQUAL(PlaceStateCheck("09:00-21:00", now), EPlaceState::CloseSoon, ());
}
UNIT_TEST(WorkingTime_Open)
{
// 1-jan-2000 13:50
std::tm when = {};
when.tm_mday = 1;
when.tm_mon = 0;
when.tm_year = 100;
when.tm_hour = 13;
when.tm_min = 50;
time_t now = std::mktime(&when);
TEST_EQUAL(PlaceStateCheck("09:00-21:00", now), EPlaceState::Open, ());
}
UNIT_TEST(WorkingTime_Closed)
{
// 1-jan-2000 06:50
std::tm when = {};
when.tm_mday = 1;
when.tm_mon = 0;
when.tm_year = 100;
when.tm_hour = 6;
when.tm_min = 50;
time_t now = std::mktime(&when);
TEST_EQUAL(PlaceStateCheck("09:00-21:00", now), EPlaceState::Closed, ());
}

View File

@@ -1,62 +0,0 @@
#pragma once
#include "3party/opening_hours/opening_hours.hpp"
#include "base/assert.hpp"
#include <chrono>
#include <ctime>
#include <string>
namespace osm
{
enum class EPlaceState
{
Open,
Closed,
OpenSoon,
CloseSoon
};
inline std::string DebugPrint(EPlaceState state)
{
switch (state)
{
case EPlaceState::Open:
return "EPlaceState::Open";
case EPlaceState::OpenSoon:
return "EPlaceState::OpenSoon";
case EPlaceState::Closed:
return "EPlaceState::Closed";
case EPlaceState::CloseSoon:
return "EPlaceState::CloseSoon";
}
UNREACHABLE();
}
inline EPlaceState PlaceStateCheck(std::string const & openingHours, time_t timestamp)
{
osmoh::OpeningHours oh(openingHours);
auto future = std::chrono::system_clock::from_time_t(timestamp);
future += std::chrono::minutes(15);
enum {OPEN = 0, CLOSED = 1};
size_t nowState = OPEN;
size_t futureState = OPEN;
// TODO(mgsergio): Switch to three-stated model instead of two-staed
// I.e. set unknown if we can't parse or can't answer whether it's open.
if (oh.IsValid())
{
nowState = oh.IsOpen(timestamp) ? OPEN : CLOSED;
futureState = oh.IsOpen(std::chrono::system_clock::to_time_t(future)) ? OPEN : CLOSED;
}
EPlaceState state[2][2] = {{EPlaceState::Open, EPlaceState::CloseSoon},
{EPlaceState::OpenSoon, EPlaceState::Closed}};
return state[nowState][futureState];
}
} // namespace osm