Como redimensionar uma exibição personalizada programaticamente?


164

Estou codificando uma exibição personalizada, estendida de RelativeLayout, e quero redimensioná-la programaticamente. Como posso fazer?

a classe de visualização personalizada é algo como:

public ActiveSlideView(Context context, AttributeSet attr){
        super(context, attr);
        LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        if(inflater != null){       
            inflater.inflate(R.layout.active_slide, this);
        }

Respostas:


253

O Android lança uma exceção se você não conseguir ultrapassar a altura ou a largura de uma exibição. Em vez de criar um novo objeto LayoutParams, use o original, para que todos os outros parâmetros definidos sejam mantidos. Observe que o tipo de LayoutParams retornado por getLayoutParams é o do layout pai , não a visualização que você está redimensionando.

RelativeLayout.LayoutParams params = (RelativeLayout.LayoutParams) someLayout.getLayoutParams();
params.height = 130;
someLayout.setLayoutParams(params);

2
Como o @HerbertD menciona, também recebo um erro ao fazer isso, a menos que eu use LinearLayout.LayoutParams, mesmo através dele é um RelativeLayout que estou redimensionando.
Martin Belcher - AtWrk

6
@Eigo De acordo com a documentação do Android, os LayoutParams são passados ​​para a tela pai, pois essa é a tela responsável pelo layout.
sstn

1
Se o valor de entrada deve ser convertido em valor de dp ou funcionaria.
Dory

Isto é também preferível, uma vez que evita instanciar um novo LayoutParams objeto desnecessariamente
Stephen Kidson

129
this.setLayoutParams(new LinearLayout.LayoutParams(LayoutParams.FILL_PARENT, theSizeIWant));

Problema resolvido!

NOTA: Certifique-se de usar os Layout dos pais LayoutParams. O meu é LinearLayout.LayoutParams!


3
Que. Por que você não usariaRelativeLayout.LayoutParams?
nmr

1
Isso não funcionou para mim, eu tenho uma exceção de elenco de classe para ele.
Tapan Thaker

4
@Tapan Thanker Use LayoutParams do layout principal. E o layout Meu pai é LinearLayout.
precisa saber é o seguinte

10
Eu escrevi uma versão mais genérica disso: private void resizeView(View view, int newWidth, int newHeight) { try { Constructor<? extends LayoutParams> ctor = view.getLayoutParams().getClass().getDeclaredConstructor(int.class, int.class); view.setLayoutParams(ctor.newInstance(newWidth, newHeight)); } catch (Exception e) { e.printStackTrace(); } }
atroutt 16/09/13

2
Isso redefinirá todos os outros parâmetros para os valores padrão. Resposta @smisiewicz é melhor.
Fran Marzoa

66

Isso funciona para mim:

ViewGroup.LayoutParams params = layout.getLayoutParams();
params.height = customHeight;
layout.requestLayout();

7
Isso é muito melhor que as outras respostas, porque esse código não exige o tipo exato do ViewGroup pai.
Bart Burg

1
Você sabe qual é a diferença entre chamar requestLayout () e chamar setLayoutParams (params)?
voghDev

2
setLayoutParams (params) inclui requestLayout ().
illusionJJ

44

Pelo que vale, digamos que você queira redimensionar a exibição em pixels independentes do dispositivo ( dp ): -

Você precisa usar um método chamado applyDimension, que é membro da classe TypedValuepara converter de pixels em dps. Então, se eu quiser definir a altura para 150dp (digamos) - então eu poderia fazer isso:

float pixels = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 150, getResources().getDisplayMetrics());
LinearLayout.LayoutParams params = (LinearLayout.LayoutParams) someLayout.getLayoutParams();
params.height = (int) pixels;
someLayout.setLayoutParams(params);

onde a expressão: getResources().getDisplayMetrics()obtém a densidade / resolução da tela


6
Em vez de codificar a sua dimensão, você também pode usar isso para a altura em pixels:float pixels = context.getResources().getDimensionPixelSize(R.dimen.card_height);
François Dermu

esta resposta é mais apropriada como resposta correta! Obrigado
Yunus Kulyyev


6

tente este:

...
View view = inflater.inflate(R.layout.active_slide, this);
view.setMinimumWidth(200);

Desculpe, não postei todas as perguntas desde que você a respondeu. Agora essa é a questão toda. Obrigado!
precisa saber é o seguinte

6

Aqui está uma versão mais genérica da solução acima em @herbertD:

private void resizeView(View view, int newWidth, int newHeight) { 
    try { 
        Constructor<? extends LayoutParams> ctor = view.getLayoutParams().getClass().getDeclaredConstructor(int.class, int.class); 
        view.setLayoutParams(ctor.newInstance(newWidth, newHeight));   
    } catch (Exception e) { 
        e.printStackTrace(); 
    }
}

@atroutt, você literalmente salvou meu dia :)
Qasim

5

Usei dessa maneira para aumentar a largura da visualização personalizada

customDrawingView.post(new Runnable() {
                            @Override
                            public void run() {
                                View view_instance = customDrawingView;
                                android.view.ViewGroup.LayoutParams params = view_instance
                                        .getLayoutParams();
                                int newLayoutWidth = customDrawingView
                                        .getWidth()
                                        + customDrawingView.getWidth();
                                params.width = newLayoutWidth;
                                view_instance.setLayoutParams(params);
                                screenWidthBackup = params.width;
                            }
                        });

4

Eu resolvi desta maneira .. Eu tenho basicamente uma visão simples dentro do arquivo xml.

 View viewname = findViewById(R.id.prod_extra);
             prodExtra.getLayoutParams().height=64;

2
haha, maneira muito ingênua, mas bem funcional, no entanto, recomendo chamar setLayoutParams () para propagar adequadamente as alterações para possíveis filhos aninhados, portanto, após atualizar .width e .height, chame view.setLayoutParams (view.getLayoutParams ()) sempre prova de tipo
comeGetSome 2/16/16

@Bhargav Rao você poderia me ajudar sobre este assunto: https://stackoverflow.com/q/44259342/6596724
smoking-world

2

Se você tiver apenas two or three condition(sizes), poderá usar o @Overide onMeasure como

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

E altere seu tamanho para essas condições na classe CustomView facilmente.


1

se você estiver substituindo onMeasure, não se esqueça de atualizar os novos tamanhos

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
    setMeasuredDimension(newWidth, newHeight);
}

1

Foi assim que consegui isso. Na resposta Sileria, ele / ela fez o seguinte:

ViewGroup.LayoutParams params = layout.getLayoutParams();
params.height = customHeight;
layout.requestLayout();

Isso está correto, mas espera que demos a altura pixels, mas eu queria dar o que dpeu queria que fosse, então adicionei:

public int convertDpToPixelInt(float dp, Context context) {
    return (int) (dp * (((float) context.getResources().getDisplayMetrics().densityDpi) / 160.0f));
}

Então será assim:

ViewGroup.LayoutParams params = layout.getLayoutParams();
params.height = convertDpToPixelInt(50, getContext());
layout.requestLayout();

0

Isto é o que eu fiz:

View myView;  
myView.getLayoutParams().height = 32;  
myView.getLayoutParams().width = 32;

Se houver um grupo de visualizações ao qual essa visualização pertence, também será necessário chamar yourViewGroup.requestLayout () para que ela entre em vigor.

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.