Skip to content

Commit 5729c29

Browse files
committed
v.1.6.4
1 parent 50e6559 commit 5729c29

File tree

13 files changed

+94
-72
lines changed

13 files changed

+94
-72
lines changed

CRAN-SUBMISSION

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
1-
Version: 1.6.3
2-
Date: 2024-01-12 05:46:46 UTC
3-
SHA: 57ef62df7605f7bbeff9750de5139f27ee8e1241
1+
Version: 1.6.4
2+
Date: 2024-06-05 02:55:49 UTC
3+
SHA: 50e6559c12e380ccbb49f99d46228467dde8ec5e

DESCRIPTION

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
Package: echarty
22
Title: Minimal R/Shiny Interface to JavaScript Library 'ECharts'
3-
Date: 2024-05-16
4-
Version: 1.6.3.03
3+
Date: 2024-06-04
4+
Version: 1.6.4
55
Author: Larry Helgason, with initial code from John Coene's library echarts4r
66
Maintainer: Larry Helgason <larry@helgasoft.com>
77
Description: Deliver the full functionality of 'ECharts' with minimal overhead. 'echarty' users build R lists for 'ECharts' API. Lean set of powerful commands.

NAMESPACE

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,5 +29,6 @@ importFrom(htmlwidgets,sizingPolicy)
2929
importFrom(stats,na.omit)
3030
importFrom(utils,askYesNo)
3131
importFrom(utils,download.file)
32+
importFrom(utils,read.csv)
3233
importFrom(utils,tail)
3334
importFrom(utils,unzip)

NEWS.md

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,15 @@
11
# history of package _echarty_
22

3-
## v. 1.6.3.03 latest in development
3+
## v. 1.6.4 latest in development
44

55
- upgrade ECharts to v.5.5.0, built with R v.4.4.0
6-
- added _nasep_ parameter to ec.data('names') for easier setting of nested lists from a _data.frame_
7-
- tested web freedom [with WebR](https://helgasoft.github.io/echarty/test/coder.html)
8-
- added explicit _leaflet_ dependency, not provided since leaflet v.2.2.0
9-
- added optional tooltip formatter (tipFmt) in _ecr.band_
6+
- add _nasep_ parameter to _ec.data('names')_ - easily set nested lists from a _data.frame_
7+
- add [WebR](https://docs.r-wasm.org/webr/latest/) support and [test](https://helgasoft.github.io/echarty/test/coder.html)
8+
- add explicit _leaflet_ dependency since dependencies changed in leaflet v.2.2.0
9+
- add optional tooltip formatter (tipFmt) in _ecr.band_
1010
- refactoring (leaflet, geo, geoJson, tests)
11+
- add debug flags for messages in JS and R
12+
- fix _crosstalk_ bug for checkboxes unselect
1113

1214
## v. 1.6.3 on CRAN
1315

R/echarty.R

Lines changed: 41 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,8 @@ noCoord <- c('polar','radar','singleAxis','parallelAxis','calendar')
3030
#' @param ctype Chart type, default is 'scatter'.
3131
#' @param preset Boolean (default TRUE). Build preset attributes like dataset, series, xAxis, yAxis, etc.
3232
#' @param series.param Additional attributes for preset series, default is NULL.\cr
33-
#' Can be used for non-timeline and timeline series (instead of _tl.series_). A single list defines one series type only.\cr
34-
#' One could also define all series directly with _series=list(list(...),list...)_ instead.
33+
#' Defines a single series type. Can be used for both non-timeline and timeline series. \cr
34+
#' Multiple series types need to be defined directly with _series=list(list(...),list...)_ or added with [ec.upd].
3535
#' @param tl.series Deprecated, use _timeline_ and _series.param_ instead.\cr
3636
#' @param ... Optional widget attributes. See Details. \cr
3737
#' @param width,height Optional valid CSS unit (like \code{'100\%'},
@@ -120,6 +120,7 @@ noCoord <- c('polar','radar','singleAxis','parallelAxis','calendar')
120120
#' )
121121
#'
122122
#' @importFrom htmlwidgets createWidget sizingPolicy getDependency JS shinyWidgetOutput shinyRenderWidget
123+
#' @importFrom utils read.csv
123124
#' @import dplyr
124125
#'
125126
#' @export
@@ -156,9 +157,11 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
156157
useDirtyRect <- if (is.null(opt1$useDirtyRect)) FALSE else opt1$useDirtyRect
157158
xtKey <- if (is.null(opt1$xtKey)) 'XkeyX' else opt1$xtKey
158159
if (xtKey=='XkeyX') df$XkeyX <- dfKey # add new column for Xtalk filtering, if needed
160+
# allow debug feedback thru cat() in JS and R code:
161+
dbg <- if (is.null(opt1$dbg)) FALSE else opt1$dbg
159162
# remove the above attributes since they are not valid ECharts options
160163
opt1$ask <- opt1$js <- opt1$renderer <- opt1$locale <- NULL
161-
opt1$useDirtyRect <- opt1$elementId <- opt1$xtKey <- NULL
164+
opt1$useDirtyRect <- opt1$elementId <- opt1$xtKey <- opt1$dbg <- NULL
162165
axis2d <- c('pictorialBar','candlestick','boxplot','scatterGL') #'custom',
163166

164167
# forward widget options using x
@@ -168,7 +171,7 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
168171
renderer = renderer,
169172
locale = locale,
170173
useDirtyRect = useDirtyRect,
171-
jcode = js,
174+
jcode = js, dbg = dbg,
172175
opts = opt1,
173176
settings = list(
174177
crosstalk_key = key,
@@ -285,11 +288,11 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
285288
return(list(x=xtem, y=ytem, z='z', c=ser$coordinateSystem))
286289
}
287290
doVMap <- function(wid) {
288-
# visualMap assist
291+
# visualMap assist: auto add min/max/calculable (categories==piecewise)
289292
vm <- wid$opts$visualMap
290293
out <- NULL
291294
if (!is.null(df) && !is.null(vm) &&
292-
is.null(vm$min) && is.null(vm$max) &&
295+
is.null(vm$min) && is.null(vm$max) && is.null(vm$categories) &&
293296
(is.null(vm$type) || (vm$type == 'continuous')) ) {
294297

295298
xx <- length(colnames(df)) # last numeric column by default
@@ -300,7 +303,6 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
300303
) xx <- 'value'
301304
if (!is.null(vm$dimension)) xx <- vm$dimension
302305
out <- list(
303-
#dimension= xx,
304306
min= min(na.omit(df[,xx])),
305307
max= max(na.omit(df[,xx])),
306308
calculable= TRUE
@@ -471,6 +473,7 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
471473
),
472474
dependencies = deps
473475
)
476+
#if (dbg) cat('\naxis2d=',axis2d)
474477

475478
tmp <- getOption('echarty.font')
476479
if (!is.null(tmp))
@@ -482,20 +485,14 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
482485

483486
# ------------- plugins loading -----------------------------
484487
opt1 <- wt$x$opts
485-
load <- opt1$load;
486-
wt$x$opts$load <- NULL
488+
load <- opt1$load; wt$x$opts$load <- NULL
487489
if (length(load)==1 && grepl(',', load, fixed=TRUE))
488490
load <- unlist(strsplit(load, ','))
489491

490492
path <- system.file('js', package= 'echarty')
491493
dep <- NULL
492494

493495
if ('world' %in% load) {
494-
dep <- htmltools::htmlDependency(
495-
name = 'world', version = '1.0.0',
496-
src = c(file = path), script= 'world.js')
497-
wt$dependencies <- append(wt$dependencies, list(dep))
498-
499496
if (preset) {
500497
wt$x$opts$xAxis <- wt$x$opts$yAxis <- NULL
501498
if (!is.null(df)) { # coordinateSystem='geo' needed for all series
@@ -511,11 +508,14 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
511508
# if (!is.null(df)) # cancelled: don't know if df first 2 cols are 'lng','lat'
512509
# wt$x$opts$geo$center= c(mean(unlist(df[,1])), mean(unlist(df[,2])))
513510
}
511+
dep <- htmltools::htmlDependency(
512+
name = 'world', version = '1.0.0',
513+
src = c(file = path), script= 'world.js')
514+
wt$dependencies <- append(wt$dependencies, list(dep))
514515
}
515-
516516
if ('leaflet' %in% load) {
517-
# coveralls pops error, win/linux ok :
518-
#stopifnot("ec.init: library 'leaflet' not installed"= file.exists(file.path(.libPaths(), 'leaflet')[[1]]))
517+
# coveralls pops error, win/linux ok :
518+
#stopifnot("ec.init: library 'leaflet' not installed"= file.exists(file.path(.libPaths(), 'leaflet')[[1]]))
519519
if (!file.exists(file.path(.libPaths(), 'leaflet')[[1]])) warning("ec.init: library 'leaflet' not installed")
520520
if (preset) {
521521
# customizations for leaflet
@@ -572,9 +572,10 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
572572
}
573573

574574
# Plugins implemented as dynamic load on-demand
575-
cdn <- 'https://cdn.jsdelivr.net/npm/'
576-
if ('3D' %in% load) {
577-
if (preset) { # replace 2D presets with 3D
575+
if (any(load %in% c('3D','liquid','gmodular','wordcloud'))) {
576+
plf <- read.csv(system.file('plugins.csv', package='echarty'), header=TRUE, stringsAsFactors=FALSE)
577+
if ('3D' %in% load) {
578+
if (preset) { # replace 2D presets with 3D
578579
isScatGL <- 'scatterGL' %in% unlist(lapply(opt1$series, \(k){k$type})) # scatterGL is 2D
579580
if (!isScatGL && is.null(opt1$globe) && is.null(opt1$geo3D) ) {
580581
wt$x$opts$xAxis <- wt$x$opts$yAxis <- NULL
@@ -593,21 +594,12 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
593594
\(s) { s$type= if (s$type=='scatter') 'scatter3D' else s$type; s })
594595
}
595596
}
596-
wt <- ec.plugjs(wt,
597-
paste0(cdn,'echarts-gl@2.0.9/dist/echarts-gl.min.js'), ask)
598-
}
599-
if ('liquid' %in% load)
600-
wt <- ec.plugjs(wt,
601-
paste0(cdn,'echarts-liquidfill@latest/dist/echarts-liquidfill.min.js'), ask)
602-
603-
if ('gmodular' %in% load)
604-
wt <- ec.plugjs(wt,
605-
paste0(cdn,'echarts-graph-modularity@latest/dist/echarts-graph-modularity.min.js'), ask)
606-
607-
if ('wordcloud' %in% load)
608-
wt <- ec.plugjs(wt,
609-
paste0(cdn,'echarts-wordcloud@latest/dist/echarts-wordcloud.min.js'), ask)
610-
597+
wt <- ec.plugjs(wt, plf[plf$name=='3D',]$url, ask)
598+
}
599+
if ('liquid' %in% load) wt <- ec.plugjs(wt, plf[plf$name=='liquid',]$url, ask)
600+
if ('gmodular' %in% load) wt <- ec.plugjs(wt, plf[plf$name=='gmodular',]$url, ask)
601+
if ('wordcloud' %in% load) wt <- ec.plugjs(wt, plf[plf$name=='wordcloud',]$url, ask)
602+
}
611603
# load unknown plugins
612604
unk <- load[! load %in% c('leaflet','custom','world','lottie','ecStat',
613605
'3D','liquid','gmodular','wordcloud')]
@@ -653,6 +645,7 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
653645
tmp <- xyNamesCS(tl.series)
654646
xtem <- tmp$x; ytem <- tmp$y
655647
if (!is.null(tmp$c)) tl.series$coordinateSystem <- tmp$c
648+
#if (dbg) cat('\ntl=',tmp$x,' ',tmp$y,' ',tmp$c)
656649

657650
if (any(c('geo','leaflet') %in% tl.series$coordinateSystem)) {
658651
klo <- 'lng'; kla <- 'lat'
@@ -670,7 +663,7 @@ ec.init <- function( df= NULL, preset= TRUE, ctype= 'scatter', ...,
670663
if (tl.series$coordinateSystem=='leaflet')
671664
wt$x$opts$leaflet$center <- center
672665
}
673-
}
666+
}
674667

675668
if (tl.series$type == 'map') {
676669
xtem <- 'name'; ytem <- 'value'
@@ -1209,9 +1202,9 @@ ec.plugjs <- function(wt=NULL, source=NULL, ask=FALSE) {
12091202
startsWith(source, 'http') || startsWith(source, 'file://'))
12101203
fname <- basename(source)
12111204
fname <- unlist(strsplit(fname, '?', fixed=TRUE))[1] # when 'X.js?key=Y'
1212-
# if (!endsWith(fname, '.js'))
1213-
# stop('ec.plugjs expecting .js suffix', call. = FALSE)
1205+
# if (!endsWith(fname, '.js')) stop('ec.plugjs expecting .js suffix', call. = FALSE)
12141206
path <- system.file('js', package = 'echarty')
1207+
12151208
ffull <- paste0(path,'/',fname)
12161209
if (!file.exists(ffull)) {
12171210
if (ask) {
@@ -1223,19 +1216,20 @@ ec.plugjs <- function(wt=NULL, source=NULL, ask=FALSE) {
12231216
if (is.na(ans)) ans <- FALSE # was cancelled
12241217
} else
12251218
ans <- TRUE
1226-
if (ans) {
1227-
try(withCallingHandlers(
1228-
download.file(source, ffull, quiet=TRUE), # method = "libcurl"),
1229-
error = function(w) { ans <- FALSE },
1230-
warning = function(w) { ans <- FALSE }
1231-
#cat('ec.plugjs Error:', sub(".+HTTP status was ", "", w, source))
1232-
)) #,silent=TRUE)
1219+
if (ans && !exists('ec.webR')) { # WebR dislikes download.file
1220+
#try(withCallingHandlers( # function(w) { ans <- FALSE }
1221+
errw <- function(w) { ans <- FALSE
1222+
cat('ec.plugjs:', sub(".+HTTP status was ", "", w, source)) }
1223+
tryCatch({
1224+
download.file(source, ffull, quiet=TRUE) }, # method = "libcurl"),
1225+
error = errw, warning = errw
1226+
)
12331227
}
12341228
if (!ans) return(wt) # error
12351229
}
12361230
dep <- htmltools::htmlDependency(
1237-
name = fname, version = '1.0.0', src = c(file = path),
1238-
script = fname
1231+
name= fname, version= '1.1.1', src= c(file = path),
1232+
script= fname
12391233
)
12401234
wt$dependencies <- append(wt$dependencies, list(dep))
12411235
return(wt)

R/util.R

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -614,6 +614,7 @@ body { padding: 10px; }
614614
#' # attribute names separator (nasep) is "_"
615615
#' df <- data.frame(name= c('A','B','C'), value= c(1,2,3),
616616
#' itemStyle_color= c('chartreuse','lightblue','pink'),
617+
#' itemStyle_decal_symbol= c('rect','diamond','none'),
617618
#' emphasis_itemStyle_color= c('darkgreen','blue','red')
618619
#' )
619620
#' ec.init(series.param= list(type='pie', data= ec.data(df, 'names', nasep='_')))
@@ -879,19 +880,23 @@ ec.data <- function(df, format='dataset', header=FALSE, ...) {
879880
stopifnot("data('names'): nasep should be 1 char"= nchar(args$nasep)==1)
880881
# names separator is present, replace compound names with nested lists
881882
tmp <- lapply(tmp, \(rr) {
883+
lst <- rr
882884
for(cc in names(rr)) {
883885
if (grepl(args$nasep, cc, fixed=T)) {
886+
lst[[cc]] <- NULL
884887
nlis <- strsplit(cc, args$nasep, fixed=T)
885888
out <- rr[[cc]];
886889
for(nn in rev(nlis[[1]][-1])) {
887-
cur <- list(); cur[[nn]] <- out;
888-
out <- cur
890+
cur <- list(); cur[[nn]] <- out; out <- cur
889891
}
890-
rr[[cc]] <- NULL
891-
rr[[ nlis[[1]][1] ]] <- out
892+
col <- nlis[[1]][1]
893+
if ( col %in% names(lst) )
894+
lst[[col]] <- .merlis(lst[[col]], out)
895+
else
896+
lst[[col]] <- out
892897
}
893898
}
894-
rr
899+
lst
895900
})
896901
}
897902
datset <- tmp;

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@ Please consider granting a Github star ⭐ to show your support.
5454
## Installation
5555

5656
<!-- [![Github version](https://img.shields.io/github/v/release/helgasoft/echarty?label=github)](https://github.com/helgasoft/echarty/releases) <sup>.02</sup> -->
57-
Latest development build **1.6.3.03**
57+
Latest development build **1.6.4**
5858

5959
``` r
6060
if (!requireNamespace('remotes')) install.packages('remotes')

inst/htmlwidgets/echarty.js

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*global HTMLWidgets, echarts, Shiny*/
2-
/*eslint no-undef: "error"*/
2+
/* eslint no-undef: "error" */
33

44
// extra functions
55
ecf = {
@@ -9,6 +9,7 @@ ecf = {
99
geoz2: 0,
1010
zoom: {s: 0, e: 100 }, // dataZoom values
1111
fs: false, // fullscreen flag Y/N
12+
dbg: false, // debug flag: if (ecf.dbg) console.log(' change s:'+v)
1213

1314
IsFullScreen: function() {
1415
var full_screen_element = document.fullscreenElement || document.webkitFullscreenElement || document.mozFullScreenElement || document.msFullscreenElement || null;
@@ -154,6 +155,7 @@ HTMLWidgets.widget({
154155
eva3 = x.jcode;
155156
}
156157
}
158+
if (x.hasOwnProperty('dbg')) { ecf.dbg= x.dbg; }
157159

158160
chart = echarts.init(document.getElementById(el.id), x.theme,
159161
{ renderer: x.renderer, locale: x.locale, useDirtyRect: x.useDirtyRect }
@@ -323,15 +325,14 @@ HTMLWidgets.widget({
323325

324326
ct_filter.on('change', function(e) { // external keys to filter
325327
if (e.sender == ct_filter) return;
326-
if (e.value == undefined) e.value = []; // sent by filter_checkbox ?!
328+
if (e.value == undefined) e.value = chart.akeys; // sent by filter_checkbox
327329

328-
rexp = (e.value.length == chart.akeys.length) //|| e.value.length == 0)
330+
rexp = (e.value.length == chart.akeys.length)
329331
? '^' : '^('+ e.value.join('|') +')$';
330332
opt = chart.getOption();
331333
dtf = opt.dataset.find(x => x.id === 'Xtalk');
332334
//dtf.transform = {type:'filter', config: {dimension: 'XkeyX', reg: rexp } }
333335
dtf.transform.config.reg = rexp;
334-
// chart.filk = e.value.map(x=>Number(x)).sort((a, b) => a - b);
335336
chart.filk = e.value.sort((a, b) => a - b);
336337
chart.setOption(opt, false);
337338
});

inst/plugins.csv

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
name,url
2+
3D,https://cdn.jsdelivr.net/npm/echarts-gl@2.0.9/dist/echarts-gl.min.js
3+
liquid,https://cdn.jsdelivr.net/npm/echarts-liquidfill@latest/dist/echarts-liquidfill.min.js
4+
gmodular,https://cdn.jsdelivr.net/npm/echarts-graph-modularity@latest/dist/echarts-graph-modularity.min.js
5+
wordcloud,https://cdn.jsdelivr.net/npm/echarts-wordcloud@latest/dist/echarts-wordcloud.min.js

man/ec.data.Rd

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)