Simple Way to Do Dynamic But Square Layout

Custom Square Layout not working as expected

You can force a square view by checking for "squareness" after layout. Add the following code to onCreate().

final View squareView = findViewById(R.id.square);
squareView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
squareView.getViewTreeObserver().removeGlobalOnLayoutListener(this);
if (squareView.getWidth() != squareView.getHeight()) {
int squareSize = Math.min(squareView.getWidth(), squareView.getHeight());
RelativeLayout.LayoutParams lp = (RelativeLayout.LayoutParams) squareView.getLayoutParams();
lp.width = squareSize;
lp.height = squareSize;
squareView.requestLayout();
}
}
});

This will force a remeasurement and layout of the square view with a specified size that replaces MATCH_PARENT. Not incredibly elegant, but it works.

enter image description here

You can also add a PreDraw listener to your custom view.

onPreDraw

boolean onPreDraw ()

Callback method to be invoked when the view tree is about to be drawn. At this point, all views in the tree have been measured and given a frame. Clients can use this to adjust their scroll bounds or even to request a new layout before drawing occurs.

Return true to proceed with the current drawing pass, or false to cancel.

Add a call to an initialization method in each constructor in the custom view:

private void init() {
this.getViewTreeObserver().addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {
@Override
public boolean onPreDraw() {
if (getWidth() != getHeight()) {
int squareSize = Math.min(getWidth(), getHeight());
RelativeLayout.LayoutParams lp = (RelativeLayout.LayoutParams) getLayoutParams();
lp.width = squareSize;
lp.height = squareSize;
requestLayout();
return false;
}
return true;
}
});
}

The XML can look like the following:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">

<TextView
android:id="@+id/text"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="300dp"
android:gravity="center"
android:text="Below is the Square Layout" />

<com.example.squareview.CustomSquareLayout
android:id="@+id/square"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_below="@id/text"
android:background="@color/colorAccent"
android:padding="16dp">

<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_centerInParent="true"
android:background="@color/colorPrimaryDark" />
</com.example.squareview.CustomSquareLayout>

</RelativeLayout>

Make a div square when there is a dynamically changing width based on percentage

This is un-tested, I do not know of how to do this in CSS only, I would use jQuery.

$('div').height($('div').width());

dynamic rectangular or square div of any size which can be fitted into a fixed size div

It's all about ratio. You need to calculate the ratio between the rectange width & frame width.

Sample code here..

function renderBox() {
const width = document.getElementById('width').value; const height = document.getElementById('height').value; const box = document.getElementById('box'); let scale = 1; while(true) { if (width <= (400 * scale) && height <= (200 * scale)) { break; } scale++; } box.style.width = width / (400 * scale) * 100 + '%'; box.style.height = height / (200 * scale) * 100 + '%'; document.getElementById('top').innerText = (200 * scale) + "px"; document.getElementById('end').innerText = (400 * scale) + "px"; }
.container {  margin-top: 20px;  width: 400px;  height: 200px;}
.frame { background-color:rgb(200,200,200); width: 100%; height: 100%;}
.scale #start { float:left;}
.scale #end { float:right;}
.scale #top { position: absolute; top: 0px; left: 10px;}
#box { background-color: red; position: relative; top: 100%; transform:translateY(-100%); left: 0;}
<div class='container'> <div class='frame'>    <div id='box'></div> </div> <div class='scale'>    <span id='top'>200px</span>    <span id='start'>0px</span>    <span id='end'>400px</span> </div></div>
<br><br>
width: <input type='number' id='width'> <br><br>height: <input type='number' id='height'> <br><Br><button onclick='renderBox()'>Render</button>

How to make a dynamic room layout accessible

Yes, grid role in your link is more appropriate, assuming that you want to layout the seats in a grid fashion.

Please read more here on the Wai Aria Practices for the Grid and Layout Grids looks more appropriate to implement for your case.

ImageView be a square with dynamic width?

The best option is to subclass ImageView yourself, overriding the measure pass:

public class SquareImageView  extends ImageView {

...

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
super.onMeasure(widthMeasureSpec, heightMeasureSpec);

int width = getMeasuredWidth();
setMeasuredDimension(width, width);
}

...

}

scaleType = centerCrop dynamically

If you need to scale the images dynamically you can use scaled bitmap method of bitmap to specifying size of your scaled down/up image programaticaly. Something like this:

Bitmap scaledBitmap = Bitmap.createScaledBitmap(unscaledBitmap, wantedWidth, wantedHeight, true);

For scaling details you can follow below link:

http://developer.sonymobile.com/2011/06/27/how-to-scale-images-for-your-android-application/

Square layout on GridLayoutManager for RecyclerView

To have the square elements in my RecyclerView, I provide a simple wrapper for my root View element; I use the following SquareRelativeLayout in place of RelativeLayout.

package net.simplyadvanced.widget;

import android.content.Context;
import android.util.AttributeSet;
import android.widget.RelativeLayout;

/** A RelativeLayout that will always be square -- same width and height,
* where the height is based off the width. */
public class SquareRelativeLayout extends RelativeLayout {

public SquareRelativeLayout(Context context) {
super(context);
}

public SquareRelativeLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}

public SquareRelativeLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}

@TargetApi(VERSION_CODES.LOLLIPOP)
public SquareRelativeLayout(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
}

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
// Set a square layout.
super.onMeasure(widthMeasureSpec, widthMeasureSpec);
}

}

Then, in my XML layout for the adapter, I've just referenced the custom view as shown in the following. Though, you can do this programmatically also.

<?xml version="1.0" encoding="utf-8"?>
<net.simplyadvanced.widget.SquareRelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/elementRootView"
android:layout_width="wrap_content"
android:layout_height="wrap_content">

<!-- More widgets here. -->

</net.simplyadvanced.widget.SquareRelativeLayout>

Note: Depending on which orientation your grid is, then you may want to have the width based off of height (GridLayoutManager.HORIZONTAL) instead of the height being based off the width (GridLayoutManager.VERTICAL).



Related Topics



Leave a reply



Submit