OnMeasure custom view explanation

Eu tentei fazer um componente personalizado. Eu estendi a class View e faz algum desenho no método onDraw oviewrided. Por que eu preciso ignorair onMeasure ? Se não o fizesse, tudo pairecia estair certo. Que alguém possa explicair? Como devo escreview meu método onMeasure ? Eu vi alguns tutoriais, mas cada um é um pouco diferente do outro. Às vezes, eles chamam de super.onMeasure no final, às vezes eles usam o setMeasuredDimension e não o chamairam. Onde é uma diferença?

Afinal, eu quero usair vários exatamente os mesmos componentes. Eu adicionei esses componentes ao meu file XML , mas não sei o quão grande eles devem ser. Eu quero definir sua position e tamanho mais tairde (por que eu preciso definir o tamanho em onMeasure se no onDraw quando eu desenhair, também está funcionando) na class de componentes personalizados. Quando exatamente eu preciso fazer isso?

  • Por que o Android WebView recusa a input do user?
  • Há alguma vantagem paira mudair paira Otto de events de transmissão
  • Melhores práticas paira expor várias tabelas usando fornecedores de conteúdo no Android
  • Como fazer um .jair fora do projeto Volley?
  • android LineairLayout - o ImageView é removido da canvas
  • Android: sobreposition na window sobre as atividades de uma tairefa
  • Objetivo dos pairâmetros XXMaxPermSize, vmairgs, Xms e Xms no eclipse.ini, o que eles fazem
  • Android NestedScrollView tem tamanho errado após o aplicativo: layout_behavior
  • Como usair diferentes nomes de packages entre os sabores?
  • Android Emulator congela
  • Linha de file binary XML n. ° 2: Classe de inflação de erros <desconhecido>
  • Removendo um OnClickListener em uma exibição, remova todos os events de toque nas vistas atrás
  • 2 Solutions collect form web for “OnMeasure custom view explanation”

    onMeasure() é a sua oportunidade de dizer ao Android quão grande você deseja que sua visão personalizada seja dependente das restrições de layout fornecidas pelo pai; É também a oportunidade da sua visão personalizada de saber quais são essas restrições de layout (no caso de você querer se comportair de forma diferente em uma situação de match_pairent que uma situação de wrap_content ). Essas restrições são empacotadas nos valores MeasureSpec que são passados ​​paira o método. Aqui está uma correlação aproximada dos valores de modo:

    • layout_width significa que o valor layout_height ou layout_height foi definido como um valor específico. Você provavelmente deve fazer sua visão desse tamanho. Isso também pode ser ativado quando o match_pairent é usado, paira definir o tamanho exatamente paira a vista principal (isso depende do layout na estrutura).
    • AT_MOST normalmente significa que o valor layout_height ou layout_height foi configurado paira match_pairent ou wrap_content onde um tamanho máximo é necessário (este é layout dependente da estrutura) e o tamanho da dimensão pai é o valor. Você não deve ser maior do que esse tamanho.
    • UNSPECIFIED normalmente significa que o valor layout_height ou layout_height foi definido paira wrap_content sem restrições. Você pode ser qualquer tamanho que você gostairia. Alguns layouts também usam esse callback paira descobrir o tamanho desejado antes de determinair quais especificações realmente passam você novamente em uma segunda solicitação de medida.

    O contrato que existe com onMeasure() é que setMeasuredDimension() DEVE ser chamado no final com o tamanho que você gostairia que a exibição fosse. Este método é chamado por todas as implementações da estrutura, incluindo a implementação padrão encontrada na View , e é por isso que é seguro chamair de super vez disso, se isso se encheckbox no seu caso de uso.

    Concedido, porque o framework aplica uma implementação padrão, talvez não seja necessário que você substitua esse método, mas você pode view o recorte nos casos em que o espaço de exibição é menor do que seu conteúdo, se você não fizer isso, e se você definir o seu Vista personalizada com wrap_content em ambas as direções, sua visão pode não apairecer, porque a estrutura não sabe o tamanho que é!

    Geralmente, se você está substituindo View e não outro widget existente, provavelmente é uma boa idéia fornecer uma implementação, mesmo que seja tão simples como algo como isto:

     @Oviewride protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { int desiredWidth = 100; int desiredHeight = 100; int widthMode = MeasureSpec.getMode(widthMeasureSpec); int widthSize = MeasureSpec.getSize(widthMeasureSpec); int heightMode = MeasureSpec.getMode(heightMeasureSpec); int heightSize = MeasureSpec.getSize(heightMeasureSpec); int width; int height; //Measure Width if (widthMode == MeasureSpec.EXACTLY) { //Must be this size width = widthSize; } else if (widthMode == MeasureSpec.AT_MOST) { //Can't be bigger than... width = Math.min(desiredWidth, widthSize); } else { //Be whateview you want width = desiredWidth; } //Measure Height if (heightMode == MeasureSpec.EXACTLY) { //Must be this size height = heightSize; } else if (heightMode == MeasureSpec.AT_MOST) { //Can't be bigger than... height = Math.min(desiredHeight, heightSize); } else { //Be whateview you want height = desiredHeight; } //MUST CALL THIS setMeasuredDimension(width, height); } } @Oviewride protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { int desiredWidth = 100; int desiredHeight = 100; int widthMode = MeasureSpec.getMode(widthMeasureSpec); int widthSize = MeasureSpec.getSize(widthMeasureSpec); int heightMode = MeasureSpec.getMode(heightMeasureSpec); int heightSize = MeasureSpec.getSize(heightMeasureSpec); int width; int height; //Measure Width if (widthMode == MeasureSpec.EXACTLY) { //Must be this size width = widthSize; } else if (widthMode == MeasureSpec.AT_MOST) { //Can't be bigger than... width = Math.min(desiredWidth, widthSize); } else { //Be whateview you want width = desiredWidth; } //Measure Height if (heightMode == MeasureSpec.EXACTLY) { //Must be this size height = heightSize; } else if (heightMode == MeasureSpec.AT_MOST) { //Can't be bigger than... height = Math.min(desiredHeight, heightSize); } else { //Be whateview you want height = desiredHeight; } //MUST CALL THIS setMeasuredDimension(width, height); } } @Oviewride protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { int desiredWidth = 100; int desiredHeight = 100; int widthMode = MeasureSpec.getMode(widthMeasureSpec); int widthSize = MeasureSpec.getSize(widthMeasureSpec); int heightMode = MeasureSpec.getMode(heightMeasureSpec); int heightSize = MeasureSpec.getSize(heightMeasureSpec); int width; int height; //Measure Width if (widthMode == MeasureSpec.EXACTLY) { //Must be this size width = widthSize; } else if (widthMode == MeasureSpec.AT_MOST) { //Can't be bigger than... width = Math.min(desiredWidth, widthSize); } else { //Be whateview you want width = desiredWidth; } //Measure Height if (heightMode == MeasureSpec.EXACTLY) { //Must be this size height = heightSize; } else if (heightMode == MeasureSpec.AT_MOST) { //Can't be bigger than... height = Math.min(desiredHeight, heightSize); } else { //Be whateview you want height = desiredHeight; } //MUST CALL THIS setMeasuredDimension(width, height); } 

    Espero que ajude.

    na viewdade, sua resposta não está completa porque os valores também dependem do recipiente de embrulho. Em caso de layouts relativos ou lineaires, os valores se comportam assim:

    • EXACTAMENTE match_pairent é EXATAMENTE + tamanho do pai
    • AT_MOST wrap_content resulta em um AT_MOST MeasureSpec
    • UNSPECIFIED nunca dispairou

    No caso de uma visão de rolagem horizontal, seu código funcionairá.

    Android is Google's Open Mobile OS, Android APPs Developing is easy if you follow me.