example: add ThemeStylerActivity

This commit is contained in:
Hannes Janetzek 2014-03-15 05:42:41 +01:00
parent 537b53d877
commit 7587c1a041
6 changed files with 307 additions and 7 deletions

View File

@ -16,7 +16,6 @@
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name" >
<!-- android:theme="@android:style/Theme.NoTitleBar.Fullscreen" -->
<activity
android:name="org.oscim.android.test.Samples"
@ -31,32 +30,32 @@
<activity
android:name="org.oscim.android.test.SimpleMapActivity"
android:theme="@android:style/Theme.NoTitleBar.Fullscreen"
android:label="@string/title_activity_map" >
</activity>
<activity
android:name="org.oscim.android.test.PathOverlayActivity"
android:theme="@android:style/Theme.NoTitleBar.Fullscreen"
android:label="@string/title_activity_map" >
</activity>
<activity
android:name="org.oscim.android.test.MarkerOverlayActivity"
android:theme="@android:style/Theme.NoTitleBar.Fullscreen"
android:label="@string/title_activity_map" >
</activity>
<activity
android:name="org.oscim.android.test.BitmapTileMapActivity"
android:theme="@android:style/Theme.NoTitleBar.Fullscreen"
android:label="@string/title_activity_map" >
</activity>
<activity
android:name="org.oscim.android.test.MapsforgeMapActivity"
android:theme="@android:style/Theme.NoTitleBar.Fullscreen"
android:label="@string/title_activity_map" >
</activity>
<activity
android:name="org.oscim.android.test.ThemeStylerActivity"
android:label="@string/title_activity_map" >
</activity>
</application>

View File

@ -0,0 +1,89 @@
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<org.oscim.android.MapView
android:id="@+id/mapView"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
</org.oscim.android.MapView>
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="vertical" >
<ToggleButton
android:id="@+id/toggleControls"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_vertical|center_horizontal|end|right"
android:onClick="onToggleControls"
android:text="@string/styler_controls_toggle" />
<LinearLayout
android:id="@+id/controls"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:background="#cc000000"
android:orientation="vertical"
android:paddingLeft="10dp"
android:paddingRight="10dp"
android:paddingTop="10dp"
android:visibility="gone" >
<SeekBar
android:id="@+id/seekBarS"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:progress="50"
android:max="100" />
<SeekBar
android:id="@+id/seekBarV"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:progress="50"
android:max="100"
android:paddingTop="10dp" />
<SeekBar
android:id="@+id/seekBarH"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="100"
android:paddingTop="10dp" />
<RadioGroup
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="horizontal" >
<RadioButton
android:id="@+id/checkBoxLine"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:checked="true"
android:onClick="onRadioButtonClicked"
android:text="@string/styler_mode_line" />
<RadioButton
android:id="@+id/checkBoxArea"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:onClick="onRadioButtonClicked"
android:text="@string/styler_mode_area" />
<RadioButton
android:id="@+id/checkBoxOutline"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:onClick="onRadioButtonClicked"
android:text="@string/styler_mode_outline" />
</RadioGroup>
</LinearLayout>
</LinearLayout>
</RelativeLayout>

View File

@ -11,5 +11,9 @@
<string name="cancel">Cancel</string>
<string name="error">Error</string>
<string name="file_invalid">The selected file is invalid.</string>
<string name="styler_mode_line">Line</string>
<string name="styler_mode_area">Area</string>
<string name="styler_mode_outline">Outline</string>
<string name="styler_controls_toggle">Controls</string>
</resources>

View File

@ -38,10 +38,20 @@ public class BaseMapActivity extends MapActivity {
private TileCache mCache;
protected final int mContentView;
public BaseMapActivity(int contentView) {
mContentView = contentView;
}
public BaseMapActivity() {
this(R.layout.activity_map);
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_map);
setContentView(mContentView);
mMapView = (MapView) findViewById(R.id.mapView);
registerMapView(mMapView);

View File

@ -45,6 +45,7 @@ public class Samples extends Activity {
linearLayout.addView(createButton(MapsforgeMapActivity.class));
linearLayout.addView(createButton(PathOverlayActivity.class));
linearLayout.addView(createButton(MarkerOverlayActivity.class));
linearLayout.addView(createButton(ThemeStylerActivity.class));
}
private Button createButton(final Class<?> clazz) {

View File

@ -0,0 +1,197 @@
package org.oscim.android.test;
import static org.oscim.utils.ColorUtil.modHsv;
import static org.oscim.utils.ColorUtil.shiftHue;
import org.oscim.layers.tile.vector.BuildingLayer;
import org.oscim.layers.tile.vector.VectorTileLayer;
import org.oscim.layers.tile.vector.labeling.LabelLayer;
import org.oscim.map.Layers;
import org.oscim.renderer.MapRenderer;
import org.oscim.theme.RenderTheme;
import org.oscim.theme.VtmThemes;
import org.oscim.theme.rule.Rule;
import org.oscim.theme.rule.Rule.RuleVisitor;
import org.oscim.theme.styles.AreaStyle;
import org.oscim.theme.styles.AreaStyle.AreaBuilder;
import org.oscim.theme.styles.LineStyle;
import org.oscim.theme.styles.LineStyle.LineBuilder;
import org.oscim.theme.styles.RenderStyle;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import android.os.Bundle;
import android.view.View;
import android.widget.RadioButton;
import android.widget.SeekBar;
import android.widget.SeekBar.OnSeekBarChangeListener;
import android.widget.ToggleButton;
public class ThemeStylerActivity extends BaseMapActivity implements OnSeekBarChangeListener {
final Logger log = LoggerFactory.getLogger(ThemeStylerActivity.class);
public ThemeStylerActivity() {
super(R.layout.activity_map_styler);
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
((SeekBar) findViewById(R.id.seekBarH)).setOnSeekBarChangeListener(this);
((SeekBar) findViewById(R.id.seekBarS)).setOnSeekBarChangeListener(this);
((SeekBar) findViewById(R.id.seekBarV)).setOnSeekBarChangeListener(this);
Layers layers = mMap.layers();
layers.add(new BuildingLayer(mMap, mBaseLayer));
layers.add(new LabelLayer(mMap, mBaseLayer));
mMap.setTheme(VtmThemes.DEFAULT);
mMap.setMapPosition(53.08, 8.83, Math.pow(2, 10));
}
class ModStyleVisitor extends RuleVisitor {
private final LineBuilder lineBuilder = new LineBuilder();
private final AreaBuilder areaBuilder = new AreaBuilder();
@Override
public void apply(Rule r) {
for (RenderStyle style : r.styles) {
if (style instanceof LineStyle) {
LineStyle s = (LineStyle) style;
HSV c = lineColor;
if (lineColor.changed && s.outline)
continue;
if (outlineColor.changed) {
if (!s.outline)
continue;
c = outlineColor;
}
s.set(lineBuilder.set(s)
.color(modColor(s.color, c))
.stippleColor(modColor(s.stippleColor, c))
.build());
continue;
}
if (areaColor.changed && style instanceof AreaStyle) {
AreaStyle s = (AreaStyle) style;
s.set(areaBuilder.set(s)
.color(modColor(s.color, areaColor))
.blendColor(modColor(s.blendColor, areaColor))
.build());
if (s.outline == null)
continue;
s.outline.set(lineBuilder.set(s.outline)
.color(modColor(s.outline.color, areaColor))
.stippleColor(modColor(s.outline.stippleColor,
areaColor))
.build());
}
}
super.apply(r);
}
}
int modColor(int color, HSV hsv) {
return modHsv(shiftHue(color, hsv.hue), 1, hsv.sat, hsv.val, true);
}
public static class HSV {
public double hue = 0;
public double sat = 1;
public double val = 1;
public boolean changed;
}
HSV lineColor = new HSV();
HSV outlineColor = new HSV();
HSV areaColor = new HSV();
ModStyleVisitor mStyleVisitor = new ModStyleVisitor();
@Override
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
if (!fromUser)
return;
int id = seekBar.getId();
boolean modLine = ((RadioButton) findViewById(R.id.checkBoxLine)).isChecked();
boolean modArea = ((RadioButton) findViewById(R.id.checkBoxArea)).isChecked();
HSV c;
if (modArea)
c = areaColor;
else if (modLine)
c = lineColor;
else
c = outlineColor;
if (id == R.id.seekBarS)
c.sat = progress / 50f;
else if (id == R.id.seekBarV)
c.val = progress / 50f;
else if (id == R.id.seekBarH)
c.hue = progress / 100f;
log.debug((modArea ? "area" : "line")
+ " h:" + c.hue
+ " s:" + c.sat
+ " v:" + c.val);
VectorTileLayer l = (VectorTileLayer) mMap.layers().get(1);
RenderTheme t = (RenderTheme) l.getTheme();
c.changed = true;
t.traverseRules(mStyleVisitor);
t.updateStyles();
c.changed = false;
if (modArea)
MapRenderer.setBackgroundColor(modColor(t.getMapBackground(), c));
mMap.render();
}
@Override
public void onStartTrackingTouch(SeekBar seekBar) {
}
@Override
public void onStopTrackingTouch(SeekBar seekBar) {
}
public void onToggleControls(View view) {
findViewById(R.id.controls).setVisibility(((ToggleButton) view).isChecked() ?
View.VISIBLE : View.GONE);
}
public void onRadioButtonClicked(View view) {
boolean checked = ((RadioButton) view).isChecked();
if (!checked)
return;
HSV c = null;
switch (view.getId()) {
case R.id.checkBoxArea:
c = areaColor;
break;
case R.id.checkBoxLine:
c = lineColor;
break;
case R.id.checkBoxOutline:
c = outlineColor;
break;
}
if (c == null)
return;
((SeekBar) findViewById(R.id.seekBarS)).setProgress((int) (c.sat * 50));
((SeekBar) findViewById(R.id.seekBarV)).setProgress((int) (c.val * 50));
((SeekBar) findViewById(R.id.seekBarH)).setProgress((int) (c.hue * 100));
}
}