open flash chart rails x-axis issue - ruby-on-rails

I am using open flash chart 2 (the plugin) in my rails application. Everything is looking smooth except for the range on my x axis. I am creating a line to represent cell phone plan cost over a specific amount of usage and I'm generate 8 values, 1-5 are below the allowed usage while 6-8 are demonstrations of the cost for usage over the limit.
The problem I'm encountering is how to set the range of the X axis in ruby on rails to something specific to the data. Right now the values being displayed are the indexes of the array that I'm giving. When I try to hand a hash to the values the chart doesn't even load at all.
So basically I need help getting a way to set the data for my line properly so that it displays correctly, right now it is treating every value as if it represents the x value of the index of the array.
Here is a screen shot which may be a better description than what I am saying: http://i163.photobucket.com/albums/t286/Xeno56/Screenshot.png Note that those values are correct just the range on the x-axis is incorrect, it should be something like 100, 200, 300, 400, 500, 600, 700
Code:
y = YAxis.new
y.set_range(0,100, 20)
x_legend = XLegend.new("Usage")
x_legend.set_style('{font-size: 20px; color: #778877}')
y_legend = YLegend.new("Cost")
y_legend.set_style('{font-size: 20px; color: #770077}')
chart =OpenFlashChart.new
chart.set_x_legend(x_legend)
chart.set_y_legend(y_legend)
chart.y_axis = y
line = Line.new
line.text = plan.name
line.width = 2
line.color = '#006633'
line.dot_size = 2
line.values = generate_data(plan)
chart.add_element(line)
def generate_data(plan)
values = []
#generate below threshold numbers
5.times do |x|
usage = plan.usage / 5 * x
cost = plan.cost
values << cost
end
#generate above threshold numbers
3.times do |x|
usage = plan.usage + ((plan.usage / 5) * x)
cost = plan.cost + (usage * plan.overage)
values << cost
end
return values
end
Also the other problem I'm having is I can't just add a few points as any values I give are taken as x being the elements position in the array and y being the value, whereas I need to be able to specify the x and y values for each point so I don't have to buffer my array with a bunch of null values

You have to create an XAxis Object to set the labels:
x = XAxis.new
x.labels = [100, 200, 300, 400, 500, 600, 700].collect(&:to_s)
chart.x_axis = x

From my experience there are many ways to do things with Open Flash Chart 2. mikezter example above is almost correct; however, this is how I set the XAxis labels.
x = XAxis.new
x.set_labels([100, 200, 300, 400, etc]).collect(&:to_s)
chart.x_axis = x
Note the only difference between my example and mikezter's is I use:
x.set_labels([array values etc])
instead of
x.labels = [array values etc]

I ended up ditching open flash chart 2 and going with Flotr

Related

Drawing a Matrix

Im trying to generate a random map using a matrix but I dont really know how. Here is the
function for the matrix. wMap and hMap are the width and height, and mapSprites is a table containing some ground sprites. Also how can I draw the matrix? Im sorry if this is too much of a question, but Im really in need for some help
function buildMap(wMap, hMap)
for i = 1, wMap do
mt[i] = {}
for j = 1, hMap do
mt[i][j] = math.random(mapSprites)
end
end
end
Generating a random map in any programming language will utilize two core concepts: The language's random function and nested for loops, two for the case of a map/matrix/2d array.
The first problem, is you may or may not have mt initialized outside the function. This function assumes the variable exists outside of the function and each time the function is called it will overwrite mt (or initialize it for the first function call) with random values.
The second problem, the width, wMap, and height, hMap, of the map are in the wrong order, as maps/matrices/2d arrays first iterate over the height (y dimension) and then the width (x dimension).
The last problem, mapSpripes also has to be declared outside the function (which is not clear with your code snippet), which will be the highest possible value the random function can generate. You can read more about math.random here: http://lua-users.org/wiki/MathLibraryTutorial
Consider this function I wrote that makes those adjustments as well as has some additional variables for the minimum and maximum random value. Of course, you can remove these to have it fit your intended purposes.
function buildMap(wMap, hMap)
local minRand = 10
local maxRand = 20
for y = 1, hMap do
matrix[y] = {}
for x = 1, wMap do
matrix[y][x] = math.random(minRand, maxRand)
end
end
end
I suggest you use this function as inspiration for your future iteratins. You can make minRand and maxRand parameters or make matrix a returned value rather than manipulating an already declared matrix value outside of the function.
Best of luck!
EDIT:
Regarding your second question. Look back at the section I wrote about nested for loops. This will be crucial to "drawing" your map. I believe you have the building blocks to resolve this issue yourself as there isn't enough context provided about what "drawing" looks like. Here is a fundamentally similiar function, based on my previous function, on printing the map:
function printMap(matrix)
for i = 1, #matrix do
for j = 1, #matrix[i] do
io.write(matrix[i][j] .. " ")
end
io.write("\n")
end
end
For choosing random sprite, I recommend you to create a table of sprites and then save index of sprite in matrix. Then you can draw it in same loop, but now, you will iterate over matrix and draw sprite based on sprite index saved in matrix in position given by matrix position (x and y in loop) times size of sprite.
local sprites, mt = {}, {}
local spriteWidth, spriteHeight = 16, 16 -- Width and height of sprites
function buildMap(wMap, hMap)
mt = {}
for i = 1, wMap do
mt[i] = {}
for j = 1, hMap do
mt[i][j] = math.random(#sprites) -- We choose random sprite index (#sprites is length of sprites table)
end
end
end
function love.load()
sprites = {
love.graphics.newImage('sprite1.png'),
love.graphics.newImage('sprite2.png'),
-- ...
}
buildMap()
end
function love.draw()
for y, row in ipairs(mt) do
for x, spriteIndex in ipairs(row) do
-- x - 1, because we want to start at 0, 0, but lua table indexing starts at 1
love.graphics.draw(sprites[spriteIndex], (x - 1) * spriteWidth, (y - 1) * spriteHeight)
end
end
end

Manim:why is my graph plotted in half the animation time?

I have this simple script, where I would like the ValueTracker (displayed as a number on the right) to evolve at the same speed with the graph. Instead the graph plotting finishes in 5 seconds. Do you know why and how to fix it?
from manim import *
class TrackerExample(Scene):
def sin(self,x):
f = 1 / 50
return np.sin(x * 2 * math.pi * f) / 2 + 0.5
def construct(self):
axes= Axes(x_range=[0, 749, 100],
y_range=[0, 4, 2],
axis_config={"include_numbers": True, "font_size": 24},
x_axis_config={},
x_length=4,
y_length=3
).move_to(LEFT * 2)
self.play(Write(axes, lag_ratio=0.01, run_time=1))
tracker = ValueTracker(0)
sin_graph = axes.plot(lambda x: self.sin(x), color=BLUE)
numbers = DecimalNumber(0).move_to(2*RIGHT)
numbers.add_updater(lambda m: m.set_value(int(tracker.get_value())))
self.add(numbers)
self.play(tracker.animate.set_value(749), Write(sin_graph), run_time=10,
rate_func=linear)
example = TrackerExample()
example.construct()
I am using the community version of manim, 0.16.0.post0
This is due to your choice of Animation: Write draws, in the first 50% of the animation run time, the stroke of the mobject and then fills it in the remaining 50% of the run time. Replace Write with Create, and it will look as expected.
And by the way, if you want to render your scene directly from the script, use the render method, not construct:
example = TrackerExample()
example.render()

Getting data from a table

Using Tiled I generated a Lua file which contains a table. So I figured that I'd write a for loop which cycles through the table gets the tile id and checks if collision is true and add collision if it was. But, I've been unable to get the tile id's or check they're properties. But it returned a error saying that I tried to index nil value tileData.
Here is the Map file
return {
version = "1.1",
luaversion = "5.1",
-- more misc. data
tilesets = {
{
name = "Tileset1",
firstgid = 1,
tilewidth = 16,
tileheight = 16,
tiles = {
{
id = 0,
properties = {
["Collision"] = false
}
},
}
}
layers = {
{
type = "tilelayer",
name = "Tile Layer 1"
data = {
-- array of tile id's
}
}
}
}
And here is the for loop I wrote to cycle through the table
require("Protyping")
local map = love.filesystem.load("Protyping.lua")()
local tileset1 = map.tilesets
local tileData = tileset1.tiles
local colision_layer = map.layers[1].data
for y=1,16 do
for x=1,16 do
if tileData[colision_layer[x*y]].properties["Colision"] == true then
world:add("collider "..x*y,x*map.tilewidth, y*tileheight,tilewidth,tileheight)
end
end
end
Try this:
tileset1 = map.tilesets[1]
instead of
tileset1 = map.tilesets
lhf's answer (map.tilesets[1] instead of map.tilesets) fixes the error you were getting, but there are at least two other things you'll need to fix for your code to work.
The first is consistent spelling: you have a Collision property in your map data and a Colision check in your code.
The second thing you'll need to fix is the way that the individual tiles are being referenced. Tiled's layer data is made of 2-dimensional tile data laid out in a 1-dimensional array from left-to-right, starting at the top, so the index numbers look like this:
You would think you could just do x * y to get the index, but if you look closely, you'll see that this doesn't work. Instead, you have to do x + (y - 1) * width.
Or if you use zero-based x and y, it looks like this:
Personally, I prefer 0-based x and y (but as I get more comfortable with Lua, that may change, as Lua has 1-based arrays). If you do go with 0-based x and y, then the formula is x + 1 + y * width.
I happen to have just written a tutorial this morning that goes over the Tiled format and has some helper functions that do exactly this (using the 0-based formula). You may find it helpful: https://github.com/prust/sti-pg-example.
The tutorial uses Simple Tiled Implementation, which is a very nice library for working with Tiled lua files. Since you're trying to do collision, I should mention that STI has a plugins for both the bump collision library and the box2d (physics) collision library.

Setting iOS-Charts Float to Integer YAxis

I tried setting yAxis to integer using NSNumberFormatter,
yAxis.valueFormatter = NSNumberFormatter()
yAxis.valueFormatter.minimumFractionDigits = 0
but the problem here is I am getting duplicate yAxis values - 0, 1, 2, 2, 3, 4 and 5.
How this can be eliminated?
These are the issues I am facing. I tried setting
barChart.leftAxis.axisMaximum = 5.0
barChart.leftAxis.axisMinimum = 0.0
barChart.leftAxis.customAxisMin = 0
barChart.leftAxis.customAxisMax = 5.0
but not helping any suggestions?
This cannot be avoided, because you don't allow fraction digit.
minimumFractionDigits = 0 means no decimal if possible, like 2.1 and 2.0, they will result in 2.1 and 2 ( if maximumFractionDigits = 1)
You need to give the information what's the raw value and what's the value of maximumFractionDigits
EDIT:
the y axis label is calculated by default via internal func computeAxisValues
it calculate the interval based on your max and min value, and the label count.
if _yAxis.isForceLabelsEnabled is enabled, then it will read labelCount and just use (max-min)/(labelCount-1) to calculate the interval. It is disabled by default.
When isForceLabelsEnabled is false, it has a small algorithm to calculate what's the proper way to get a good looking number.
Take a look at internal func computeAxisValues to find out what meets your need.
Update for your second part of question:
you should not touch axisMaximum nor min
enable forceLabelsEnabled
change yAxis.labelCount to 6 or 5 or whatever you like
enable xAxis.wordWrapEnabled

Dealing with Bubble Chart overlap

We're working on a Highcharts Bubble Chart w/category axis and a lot of overlapping data points. Is there any way to control exactly how the bubbles are placed within the category? What we'd like to do is sort the bubbles ahead of time and then offset them from each other a bit. Some overlap is desirable so we'd prefer to not have to add additional categories to make sure there is no overlap.
Unfortunately we have no solution for controling positions of the bubbles. But you can request your propositin in our uservoice system http://highcharts.uservoice.com/
If you are using categories, your x values are the array index of the category for your value.
So to tweak the placement, you can tweak your x value by adding/subtracting small decimal amounts:
http://jsfiddle.net/yPLVP/10/
[-0.1,2,10]
Keeping in mind that +/- .5 is the center point between the categories - so for a value that falls within the 3rd category (x value 2), keep your x values between 1.55 and 2.45 (or so....)
I have the same problem, you can add this code:
function(chartObj) {
$.each(chartObj.series[0].data, function(i, point) {
var aux = 0;
if (i % 2 == 0)
aux = point.dataLabel.y + 6;
else
aux = point.dataLabel.y - 6;
point.dataLabel.attr({y:aux});
});
jsFiddle: http://jsfiddle.net/9m6wu/277/

Resources