Folium changes default marker icon to info sign when adding color - marker

I am creating map of servers from a list. I have a function that filters these server and I would like to change marker color based on these filters. However, when I add color to marker as seen bellow, marker icon changes to info-sign and color is ignored. Anyone please know how to bypass this problem?
for node in nodes:
name = node[2]
if node[-2] == 'unknown' or node[-1] == 'unknown':
continue
x = float(node[-2])
y = float(node[-1])
text = """
NODE: %s, IP: %s
URL: %s
FULL NAME: %s
LATITUDE: %s, LONGITUDE: %s
""" % (node[2],
node[1],
node[7],
node[8],
node[9],
node[10])
popup = folium.Popup(text.strip().replace('\n', '<br>'), max_width=1000)
folium.Marker([x, y],popup=popup, icon=folium.Icon(color=color)).add_to(map_full)
map_full.save('plbmng_server_map.html')
color is set at the beginning and can be one of the ['yellow', 'blue', 'red']

You could always just add icon='None' to your arguments for folium.Icon().
Also be aware of the difference between color and icon_color.

Related

How do I dynamically change label text color of R Shiny radioButtons widget when users select an option?

I am building a Shiny App where users have to complete several mandatory questions in the form of radioButtons, numericInputs, and textInputs in order to generate an output. To highlight which questions still need to be completed, I would like the label text to initially be rendered as "red", but then switch to "black" once a value has been selected and/or inputted into the widgets.
library(shiny)
ui <- fluidPage(
sidebarPanel(
radioButtons("my_radio_button", tags$p("Choose an Option", style = "color:red;"), choices = c("Option 1", "Option 2"), selected = character(0)),
)
)
server <- function(input, output, session) {
observeEvent(input$val, {
x <- input$my_radio_button
if (x == "Option 1" | x == "Option 2") {
## MAKE "Choose an Option" LABEL TURN BLACK
}
})
}
shinyApp(ui, server)
I found this example on stack exchange (R shiny conditionally change numericInput background colour) where they conditionally changed the background colour of the widget, but I don't know enough about programming to modify it to change the label text instead.
Any help would be greatly appreciated. Thanks!
You can use shinyjs
add shinyjs::useShinyjs() to the beginning of ui
add an id to the label param of the radioButtons ui element. I've used r_label in the example below
Observe for changes to input$my_radio_button, which trigger calls to shinyjs::html()
Full code below:
library(shiny)
library(shinyjs)
ui <- fluidPage(
shinyjs::useShinyjs(),
sidebarPanel(
radioButtons("my_radio_button",
label=tags$p("Choose an Option", style = "color:red;", id="r_label"),
choices = c("Option 1", "Option 2"), selected = character(0)),
)
)
server <- function(input, output, session) {
observeEvent(input$my_radio_button, {
shinyjs::html("r_label", "<p style='color:black'>Choose an Option</p>")
})
}
shinyApp(ui, server)

html2pdf fit image to pdf

I finally got my html2pdf to work showing my web page just how I want it in the pdf(Any other size was not showing right so I kept adjusting the format size until it all fit properly), and the end result is exactly what I want it to look like... EXCEPT even though my aspect ratio is correct for a landscape, it is still using a very large image and the pdf is not standard letter size (Or a4 for that matter), it is the size I set. This makes for a larger pdf than necessary and does not print well unless we adjust it for the printer. I basically want this exact image just converted to a a4 or letter size to make a smaller pdf. If I don't use the size I set though things are cut off.
Anyway to take this pdf that is generated and resize to be an a4 size(Still fitting the image on it). Everything I try is not working, and I feel like I am missing something simple.
const el = document.getElementById("test);
var opt = {
margin: [10, 10, 10, 10],
filename: label,
image: { type: "jpeg", quality: 0.98 },
//pagebreak: { mode: ["avoid-all", "css"], after: ".newPage" },
pagebreak: {
mode: ["css"],
avoid: ["tr"],
// mode: ["legacy"],
after: ".newPage",
before: ".newPrior"
},
/*pagebreak: {
before: ".newPage",
avoid: ["h2", "tr", "h3", "h4", ".field"]
},*/
html2canvas: {
scale: 2,
logging: true,
dpi: 192,
letterRendering: true
},
jsPDF: {
unit: "mm",
format: [463, 600],
orientation: "landscape"
}
};
var doc = html2pdf()
.from(el)
.set(opt)
.toContainer()
.toCanvas()
.toImg()
.toPdf()
.save()
I have been struggling with this a lot as well. In the end I was able to resolve the issue for me. What did the trick for me was setting the width-property in html2canvas. My application has a fixed width, and setting the width of html2canvas to the width of my application, scaled the PDF to fit on an A4 paper.
html2canvas: { width: element_width},
Try adding the above option to see if it works. Try to find out the width of your print area in pixels and replace element_width with that width.
For completeness: I am using Plotly Dash to create web user interfaces. On my interface I include a button that when clicked generates a PDF report of my dashboard. Below I added the code that I used for this, in case anybody is looking for a Dash solution. To get this working in Dash, download html2pdf.bundlemin.js and copy it to the assets/ folder. The PDF file will be downloaded to the browsers default downloads folder (it might give a download prompt, however that wasn't how it worked for me).
from dash import html, clientside_callback
import dash_bootstrap_components as dbc
# Define your Dash app in the regular way
# In the layout define a component that will trigger the download of the
# PDF report. In this example a button will be responsible.
app.layout = html.Div(
id='main_container',
children = [
dbc.Button(
id='button_download_report',
children='Download PDF report',
className='me-1')
])
# Clientside callbacks allow you to directly insert Javascript code in your
# dashboards. There are also other ways, like including your own js files
# in the assets/ directory.
clientside_callback(
'''
function (button_clicked) {
if (button_clicked > 0) {
// Get the element that you want to print. In this example the
// whole dashboard is printed
var element = document.getElementById("main_container")
// create a date-time string to use for the filename
const d = new Date();
var month = (d.getMonth() + 1).toString()
if (month.length == 1) {
month = "0" + month
}
let text = d.getFullYear().toString() + month + d.getDay() + '-' + d.getHours() + d.getMinutes();
// Set the options to be used when printing the PDF
var main_container_width = element.style.width;
var opt = {
margin: 10,
filename: text + '_my-dashboard.pdf',
image: { type: 'jpeg', quality: 0.98 },
html2canvas: { scale: 3, width: main_container_width, dpi: 300 },
jsPDF: { unit: 'mm', format: 'A4', orientation: 'p' },
// Set pagebreaks if you like. It didn't work out well for me.
// pagebreak: { mode: ['avoid-all'] }
};
// Execute the save command.
html2pdf().from(element).set(opt).save();
}
}
''',
Output(component_id='button_download_report', component_property='n_clicks'),
Input(component_id='button_download_report', component_property='n_clicks')
)

Update plot according to updated slider value wit Gtk

In Julia, I'd like to update a plot upon the change of value in a Gtk Slider. I understand that this has to do with the "change-value" signal in https://developer.gnome.org/gtk2/2.24/GtkRange.html#GtkRange-value-changed. However, as a beginner, I do not know how to implement the code
The “change-value” signal
gboolean
user_function (GtkRange *range,
GtkScrollType scroll,
gdouble value,
gpointer user_data)
to achieve what I wanted to do. Could anyone kindly provide an example how to use the "change-value" signal?
I know how to set up a window for the slider
sl = slider(1:11)
win = Window("Testing") |> (bx = Box(:v))
push!(bx, sl)
Gtk.showall(win)
I also know what kind of function I need to update the plot
function update(val)
int_val = int(val)
if Signal(sl) != int_val
x = range(0., 2*pi, step=0.01)
y = map(sin, x)
PyPlot.plot(x,Signal(sl)*y)
end
end
However, I don't know how or where I can trigger the "update" function to take actual action.
Thanks!
Thanks, liberforce for your advice!
Here is my minimal working example:
'''
using Gtk
# Set up scale (slider) and window
sl = GtkScale(false, 0:10)
win = Gtk.Window("Gain Selection") |> (bx = Gtk.Box(:v))
push!(bx, sl)
Gtk.showall(win)
# Connect with value-changed signal
id = signal_connect(sl, "value-changed") do widget
# Get scale value
sub = Gtk.GAccessor.adjustment(widget)
val = Gtk.get_gtk_property(sub,"value",Int64)
# Perform function related to the scale value.
println("Gain is changed to ", val)
end
push!(bx, sl)
Gtk.showall(win);
'''
Reference:
signal connect: http://juliagraphics.github.io/Gtk.jl/latest/manual/signals.html
GtkScale: https://lazka.github.io/pgi-docs/Gtk-3.0/classes/Scale.html
Extract scale value: https://discourse.julialang.org/t/how-to-get-the-current-value-of-a-gtk-scale-widget/15680
Julia Do-block: https://www.juliabloggers.com/julia-do-block-vs-python-with-statement/

Numbers in map marker in Folium

i want to display some geo locations on map, but i want the map-pin icon to display numbers instead of the default map pin.
Is there any way to do that?
I checked in font awesome icons but it didn't work.
Below is my code:
import folium
m = folium.Map(
location=[45.3288, -121.6625],
zoom_start=12,
#tiles='Mapbox Bright'
)
folium.Marker([45.3288, -121.6625], popup='<i>Mt. Hood Meadows</i>').add_to(m)
folium.Marker([45.3311, -121.7113], popup='<b>Timberline Lodge</b>',icon=folium.Icon(color='red')).add_to(m)
m
What i want is instead of this default map marker i want to include numbers in my marker instead of info-sign
Something like this:
i couldn't find the answer anywhere. Any leads on this?
display number 1 to 9 inside map marker pin
I was attempting something similar on a recent project and this is what I came up with. Might work for you.
It plots a DivCon marker with html and then a transparent circle marker in the same location.
import folium
from folium.features import DivIcon
m = folium.Map(
location=[45.3288, -121.6625],
zoom_start=12,
#tiles='Mapbox Bright'
)
p1 = [45.3288, -121.6625]
folium.Marker(p1, icon=DivIcon(
icon_size=(150,36),
icon_anchor=(7,20),
html='<div style="font-size: 18pt; color : black">1</div>',
)).add_to(m)
m.add_child(folium.CircleMarker(p1, radius=15))
p2 = [45.3311, -121.7113]
folium.Marker(p2, icon=DivIcon(
icon_size=(150,36),
icon_anchor=(7,20),
html='<div style="font-size: 18pt; color : black">2</div>',
)).add_to(m)
m.add_child(folium.CircleMarker(p2, radius=15))
Adapting the previous answer by #bob I found a solution that fit my needs. I put it below in case it is useful for anyone:
import folium
from folium.features import DivIcon
def number_DivIcon(color,number):
""" Create a 'numbered' icon
"""
icon = DivIcon(
icon_size=(150,36),
icon_anchor=(14,40),
# html='<div style="font-size: 18pt; align:center, color : black">' + '{:02d}'.format(num+1) + '</div>',
html="""<span class="fa-stack " style="font-size: 12pt" >>
<!-- The icon that will wrap the number -->
<span class="fa fa-circle-o fa-stack-2x" style="color : {:s}"></span>
<!-- a strong element with the custom content, in this case a number -->
<strong class="fa-stack-1x">
{:02d}
</strong>
</span>""".format(color,number)
)
return icon
col_hex = ['#440154',
'#481a6c',
'#472f7d',
'#414487',
'#39568c',
'#31688e',
'#2a788e',
'#23888e',
'#1f988b',
'#22a884',
'#35b779',
'#54c568',
'#7ad151',
'#a5db36',
'#d2e21b']
num = 0
loc = (43.613, 3.888)
fm = folium.Map(location=loc, tiles="Stamen Terrain")
folium.Marker(
location=loc,
popup="Delivery " + '{:02d}'.format(num+1),
icon=folium.Icon(color='white',icon_color='white'),
markerColor=col_hex[num],
).add_to(fm)
folium.Marker(
location=loc,
popup="Delivery " + '{:02d}'.format(num+1),
icon= number_DivIcon(col_hex[num],num+1)
).add_to(fm)
fm
I need these numbers (1,2) to be dynamic, meaning, I have a for loop, I want index value to be printed in the HTML line
for point in range(0, len(coordinates_st)):
# showing number
folium.Marker(location=[72.89, -124.59+2], icon=DivIcon(
icon_size=(150, 36),
icon_anchor=(7, 20),
html='<div style="font-size: 18pt; color : black">r{point}</div>',
)).add_to(map_st)

Photoshop Automation of alignment of text layer with image

I have never scripted in photoshop before, so I am wondering if this is possible. The following is currently done manually for over than 300 files. The next time round is for 600 files, therefore I am looking into automating it.
Steps:
Make Image Size to 54pixels Hight and 500px Width -- Found that this is doable.
Align Image Left.
Create a text layer and insert text -- Found that this is doable.
Align Text layer 1px to the right of the image.
Trim empty space.
Would appreciate any help and pointers. Thanks.
This script will get you started: Note that in your request you didn't mention what what the original image was going to be and shrinking it to 500 x 54 is going to stretch it one way or another. Step 2, Align the image left, was omitted as you didn't mention what you are aligning this image to. I suspect you are dealing with a large image and what to shrink it down (as long as it's not smaller than 500 x 54) and work from there. I've also omitted stage 4 as I've hard coded the position of the text to be 1 px from the right hand edge (and it vertically centered with Arial font size 18)
Anhyoo.. you should be able to alter the script to your needs.
// set the source document
srcDoc = app.activeDocument;
//set preference units
var originalRulerPref = app.preferences.rulerUnits;
var originalTypePref = app.preferences.typeUnits;
app.preferences.rulerUnits = Units.POINTS;
app.preferences.typeUnits = TypeUnits.POINTS;
// resize image (ignoring the original aspect ratio)
var w = 500;
var h = 54;
var resizeRes = 72;
var resizeMethod = ResampleMethod.BICUBIC;
srcDoc.resizeImage(w, h, resizeRes, resizeMethod)
//create the text
var textStr = "Some text";
createText("Arial-BoldMT", 18.0, 0,0,0, textStr, w-1, 34)
srcDoc.activeLayer.textItem.justification = Justification.RIGHT
//set preference units back to normal
app.preferences.rulerUnits = originalRulerPref;
app.preferences.typeUnits = originalTypePref;
//trim image to transparent width
app.activeDocument.trim(TrimType.TRANSPARENT, true, true, true, true);
// function CREATE TEXT(typeface, size, R, G, B, text content, text X pos, text Y pos)
// --------------------------------------------------------
function createText(fface, size, colR, colG, colB, content, tX, tY)
{
// Add a new layer in the new document
var artLayerRef = srcDoc.artLayers.add()
// Specify that the layer is a text layer
artLayerRef.kind = LayerKind.TEXT
//This section defines the color of the hello world text
textColor = new SolidColor();
textColor.rgb.red = colR;
textColor.rgb.green = colG;
textColor.rgb.blue = colB;
//Get a reference to the text item so that we can add the text and format it a bit
textItemRef = artLayerRef.textItem
textItemRef.font = fface;
textItemRef.contents = content;
textItemRef.color = textColor;
textItemRef.size = size
textItemRef.position = new Array(tX, tY) //pixels from the left, pixels from the top
}
Everything you listed is doable in a script. I suggest you start by reading 'Adobe Intro To Scripting' in your ExtendScript Toolkit program files directory (e.g. C:\Program Files (x86)\Adobe\Adobe Utilities - CS6\ExtendScript Toolkit CS6\SDK\English)