change child framelayout height,width,gravity programmatically?
I have linearlayout as parent and framelayout as child now I want to change height and width of framelayout programmatically
code I tried but does not effect at all
public void frame_params(FrameLayout bottomFrameLayout, int weight, int height) {
bottomFrameLayout = new FrameLayout(context);
LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(weight, height);
lp.gravity = Gravity.BOTTOM | Gravity.LEFT;
bottomFrameLayout.setLayoutParams(lp);
}
xml
<LinearLayout
android:orientation="horizontal"
android:id="#+id/relativelayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_above="#+id/hv_effect"
android:layout_below="#+id/effect_hedaer_toolbar">
<FrameLayout
android:id="#+id/FrameLayout"
android:layout_width="280dp"
android:layout_height="300dp"
android:layout_alignParentBottom="true"
android:layout_alignParentLeft="true"
android:layout_centerInParent="true"
android:layout_gravity="bottom|left">
</FrameLayout>
</Linearlayout>
I believe this line is your problem:
bottomFrameLayout = new FrameLayout(context);
In the frame_params method, you receive a FrameLayout. But, then, you instantiate a NEW one with that line. So, indeed, the FrameLayout inside the LinearLayout will continue the same way, because you are not changing it, you are creating a new FrameLayout and you're setting the parameters to it. Just try removing the aforementioned line, like this:
public void frame_params(FrameLayout bottomFrameLayout, int weight, int height) {
LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(weight, height);
lp.gravity = Gravity.BOTTOM | Gravity.LEFT;
bottomFrameLayout.setLayoutParams(lp);
}
And, then, pass the correct FrameLayout (the one with the id "FrameLayout", as specified in your xml), it should work.
Let me know if it worked, and, if it did, remember to upvote/select as the correct answer, cheers : )
Related
i am having the same problem as this guy - my bar chart will only accept a fixed height in dp. If I use Fill-Parent, match_parent or wrap_content, the chart will be flat with a height of zero. And working with fixed sizes will not work on different screen sizes.
While this question is already floating around the internet (f.i. here), no one seems to have a decent solution. Any ideas?
android:fillViewport="true" did not help either.
My XML:
<?xml version="1.0" encoding="utf-8"?>
<layout>
<FrameLayout 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"
android:paddingBottom="16dp"
android:paddingLeft="16dp"
android:paddingRight="16dp"
android:paddingTop="16dp"
tools:context="com.example.myself.myroom.Frontend.StatisticFragment">
<com.github.mikephil.charting.charts.BarChart
android:id="#+id/testchart"
android:layout_width="fill_parent"
android:layout_height="fill_parent"(or fixed number of dp) />
</FrameLayout> </layout>
the according fragment(only the chart part):
protected void onPostExecute(List<ItemS> result) {
// update the UI after background processes completes
List<ItemS> dataObjects = result;
List<BarEntry> entries = new ArrayList<BarEntry>();
final List<String> labels = new ArrayList<String>();
Integer testdummy = 0;
for (ItemS data : dataObjects) {
// turn your data into Entry objects
entries.add(new BarEntry( testdummy, data.get_dAmount().floatValue() ));
labels.add(data.getiCatID().toString());
testdummy++;
}
BarData data = new BarData(new BarDataSet(entries, "Labelerik"));
IAxisValueFormatter formatter = new IAxisValueFormatter() {
#Override
public String getFormattedValue(float value, AxisBase axis) {
return labels.get((int) value);
}
// we don't draw numbers, so no decimal digits needed
//#Override
//public int getDecimalDigits() { return 0; }
};
data.setBarWidth(0.9f); // set custom bar width
oBinding.testchart.setData(data);
oBinding.testchart.setFitBars(true); // make the x-axis fit exactly all bars
oBinding.testchart.getXAxis().setPosition(XAxis.XAxisPosition.BOTTOM);
oBinding.testchart.getXAxis().setGranularity(1f); // minimum axis-step (interval) is 1
oBinding.testchart.getXAxis().setValueFormatter(formatter);
oBinding.testchart.invalidate(); // refresh
}
Thanks for reading!
I'm trying to make a custom GTK widget in Vala, but I'm already failing at the very first basic attempt, so I'd like some help in knowing where I'm going wrong. I feel like I must be missing something painstakingly obvious, but I just can't see it.
I have three files with the following contents:
start.vala:
using Gtk;
namespace WTF
{
MainWindow main_window;
int main(string[] args)
{
Gtk.init(ref args);
main_window = new MainWindow();
Gtk.main();
return 0;
}
}
main_window.vala:
using Gtk;
namespace WTF
{
public class MainWindow : Window
{
public MainWindow()
{
/* */
Entry entry = new Entry();
entry.set_text("Yo!");
this.add(entry);
/* */
/*
CustomWidget cw = new CustomWidget();
this.add(cw);
/* */
this.window_position = WindowPosition.CENTER;
this.set_default_size(400, 200);
this.destroy.connect(Gtk.main_quit);
this.show_all();
}
}
}
custom_widget.vala:
using Gtk;
namespace WTF
{
public class CustomWidget : Bin
{
public CustomWidget()
{
Entry entry = new Entry();
entry.set_text("Yo");
this.add(entry);
this.show_all();
}
}
}
As you can see, in main_window.vala, I have two sets of code. One that adds the Entry widget directly, and one that adds my custom widget. If you run the one that adds the Entry widget directly, you get this result:
If you run the one with the custom widget, however, you get this result:
Just for the record, this is the complication command I use:
valac --pkg gtk+-2.0 start.vala main_window.vala custom_widget.vala -o wtf
EDIT:
Following user4815162342's suggestion, I implemented the size_allocate method on my custom Bin widget, like so:
public override void size_allocate(Gdk.Rectangle r)
{
stdout.printf("Size_allocate: %d,%d ; %d,%d\n", r.x, r.y, r.width, r.height);
Allocation a = Allocation() { x = r.x, y = r.y, width = r.width, height = r.height };
this.set_allocation(a);
stdout.printf("\tHas child: %s\n", this.child != null ? "true" : "false");
if (this.child != null)
{
int border_width = (int)this.border_width;
Gdk.Rectangle cr = Gdk.Rectangle()
{
x = r.x + border_width,
y = r.y + border_width,
width = r.width - 2 * border_width,
height = r.height - 2 * border_width
};
stdout.printf("\tChild size allocate: %d,%d ; %d, %d\n", cr.x, cr.y, cr.width, cr.height);
this.child.size_allocate(cr);
}
}
It writes the following in the console:
Size_allocate: 0,0 ; 400,200
Has child: true
Child size allocate: 0,0 ; 400, 200
And the window renders thusly:
GtkBin is an abstract single-child container, typically intended to decorate the child widget in some way, or change its visibility or size. Without some added value, a single-child container would be indistinguishable from the widget it contains and therefore not very useful.
Since GtkBin doesn't know what kind of decorations you will draw around the child, it expects you to implement your own size_allocate. A simple implementation is available in gtk_event_area_size_allocate, a more complex one in gtk_button_size_allocate.
This answer shows a minimal size_allocate implementation in PyGTK which should be straightforward to port to Vala. If you do anything more complex than that, you will need to also implement expose, and possibly other methods, but this will get you started.
Is there any (straightforward) way to solve the dynamic registration issue with multitouch scaling events in flex? I just can't wrap my head around this.
What I've got is (amongst some lines and labels) a path in a group that itself is wrapped in a scroller;
<s:Scroller id="scroller">
<s:Group id="scrollerContent">
<s:Path id="path">
<s:stroke>
<s:SolidColorStroke color="#ffffff" weight="2"/>
</s:stroke>
</s:Path>
</s:Group>
</s:Scroller>
What I'd like to do is to zoom in and out on the path (and the other stuff in the scrollerContent group), so in my creationComplete() method I added an eventListener to the scrollerContent group:
scrollerContent.addEventListener(TransformGestureEvent.GESTURE_ZOOM, zoomEvent);
Here is the code Christophe Coenraets provided for his chart example (which does in fact scale the path, based on x=0 though;
private function zoomEvent(e:TransformGestureEvent):void
{
zoom(e.scaleX, e.scaleY);
}
protected function zoom(scaleX:Number):void
{
var w:Number = path.width * scaleX;
if (scaleX>1)
path.width = w > width*5 ? width*5 : w;
else
{
path.width = w < width ? width : w;
if (path.x + path.width < width) path.x = width - path.width;
}
}
I'm aware of the DynamicRegistration class, but can't get it working properly, it still scales the path based on the x=0 point.
DynamicRegistration.scale(scrollerContent, new Point(e.localX, e.localY), scrollerContent.scaleX*= e.scaleX, scrollerContent.scaleY=1);
Any help regarding this would be much appreciated!
I used the DynamicRegistration class, and got it working like this, if you're still interested:
protected function onZoom(e:TransformGestureEvent, img:Image):void
{
DynamicRegistration.scale(img, new Point(e.localX, e.localY), img.scaleX*e.scaleX, img.scaleY*e.scaleY);
}
Or with the native flex method:
protected function onZoom(e:TransformGestureEvent, img:Image):void
{
img.transformAround(new Vector3D(e.localX, e.localY, 0), new Vector3D(img.scaleX*e.scaleX, img.scaleY*e.scaleY, 0));
}
The program lets the user type in a command in a textfield then whatever they typed will show in the text area. If it is keywords such as yes it will turn green, however I cannot set just one line of text green in a text area so I need to use a text pane.
The problem is that if I use a text pane I can't use the append method anymore.
private final static String newline = "\n";
private void enterPressed(java.awt.event.KeyEvent evt) {
int key = evt.getKeyCode();
if (key == KeyEvent.VK_ENTER)
{
String textfieldEnterdValue = textfield1.getText().toString();
this.TextArea1.append("> "+tb1EnterdValue+newline);
this.tb1.setText("");
if((tb1EnterdValue.equals("yes")) )
{
TextArea1.setForeground(Color.green);
}
}
JTextPane uses Document as a model. This is necessary to support the use of multiple colors and fonts.
So, to append to a JTextPane, you need to modify the Document.
The following methods are available :
insertString(int pos, String value, AttributeSet att)
remove(int pos, int length)
For example, this will append value to the end of the document.
Document d = textPane.getDocument();
d.insertString(d.getLength(), value, null);
Additionally, you may want to call scrollRectToVisible(Rectangle) with the result of modelToView(int) to ensure the newly added line is on screen.
I think you'll need to do that directly on the underlying document.
Something like this:
String value = textfield1.getText(); // no need for toString() here!
textPane.getDocument().insertString(textPane.getCaretPosition(), value, null);
I'm setting selected element in s:List component with Actionscript, it works, but List doesn't scroll to selected item -- need to scroll with scrollbar or mouse. Is it possible to auto-scroll to selected item ? Thanks !
Try the s:List method ensureIndexIsVisible(index:int):void.
For Spark:
list.ensureIndexIsVisible(index);
This function will scroll to the top of the list in Flex 4+. It takes in account the height of the item, so it will work for lists with different items with different height.
private function scrollToIndex(list:List,index:int):void
{
if (!list.layout)
return;
var dataGroup:DataGroup = list.dataGroup;
var spDelta:Point = dataGroup.layout.getScrollPositionDeltaToElement(index);
if (spDelta)
{
dataGroup.horizontalScrollPosition += spDelta.x;
//move it to the top if the list has enough items
if(spDelta.y > 0)
{
var maxVSP:Number = dataGroup.contentHeight - dataGroup.height;
var itemBounds:Rectangle = list.layout.getElementBounds(index);
var newHeight:Number = dataGroup.verticalScrollPosition + spDelta.y
+ dataGroup.height - itemBounds.height;
dataGroup.verticalScrollPosition = Math.min(maxVSP, newHeight);
}
else
{
dataGroup.verticalScrollPosition += spDelta.y;
}
}
}
//try this
this.callLater(updateIndex);//where you want to set the selectedIndex
private function updateIndex():void
{
list.selectedIndex = newIndex;
list.ensureIndexIsVisible(newIndex);
}
In flex-3 there is a scrollToIndex method and hence you can call
list.scrollToIndex(list.selectedIndex);
I believe this should work in flex-4 too.
This worked for me. had to use the callLater.
list.selectedItem = "MyTestItem"; //or list.selectedIndex = 10;
this.callLater(updateIndex); //dispatch an update to list
private function updateIndex():void {
list.ensureIndexIsVisible(list.selectedIndex);
}
I saw this basic idea here...
http://arthurnn.com/blog/2011/01/12/coverflow-layout-for-flex-4/
public function scrollGroup( n : int ) : void
{
var scrollPoint : Point = theList.layout.getScrollPositionDeltaToElement( n );
var duration : Number = ( Math.max( scrollPoint.x, theList.layout.target.horizontalScrollPosition ) - Math.min( scrollPoint.x, theList.layout.target.horizontalScrollPosition )) * .01;
Tweener.addTween(theList.layout,{ horizontalScrollPosition: scrollPoint.x , time:duration});
}
protected function theList_caretChangeHandler(event:IndexChangeEvent):void
{
scrollGroup( event.newIndex );
event.target.invalidateDisplayList();
}
You'll probably want to access the List's scroller directly and do something like:
list.scroller.scrollRect.y = list.itemRenderer.height * index;
You can multiply the height of an element by its index and pass this value to:
yourListID.scroller.viewport.verticalScrollPosition
It is a bug - you can see the demonstration and a workaround at the https://issues.apache.org/jira/browse/FLEX-33660
This custom List component extension worked for me:
<s:List
xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
valueCommit="callLater(ensureIndexIsVisible, [selectedIndex])">
</s:List>
I recently accomplished this in one of my projects by having a defined size for my items in the group..
<s:Scroller x="940" y="0" maxHeight="465" maxWidth="940" horizontalScrollPolicy="off" verticalScrollPolicy="off">
<s:HGroup id="tutPane" columnWidth="940" variableColumnWidth="false" gap="0" x="0" y="0">
</s:HGroup>
</s:Scroller>
Following this my button controls for manipulation worked by incrementing a private "targetindex" variable, then I called a checkAnimation function, which used the Animate class, in combo with a SimpleMotionPath and a comparison between tutpane.firstIndexInView and target index. This modified the "horizontalScrollPosition" of the group.
This allowed separate controls to essentially act as a scroll bar, but I had the requirement of sliding the control to view the selected item.. I believe this technique could work for automated selection of items as well