Filtros de imagem e vídeo como o Snapchat no Android

9

Estou desenvolvendo um aplicativo no qual eu quero que os filtros sejam aplicados da mesma forma que o Snapchat, Pelo que eu entendo é que eles estão usando o PagerAdapter, mas eu não sei como eles estão aplicando filtros na imagem ou vídeos e não outra imagem com filtro aplicado a ela. Qualquer ideia ou trecho de código que pode fazer o mesmo é muito apreciado por imagens e vídeos e salvá-los também. Obrigado: D

    
por PunK _l_ RuLz 13.08.2015 в 08:42
fonte

2 respostas

2

O que estou fazendo aqui é sobrepor dois bitmaps um sobre o outro. Quanto dos bitmaps devem estar visíveis, é determinado usando o toque do usuário. Eu tenho um enum para qual direção o usuário está rolando basicamente ESQUERDA OU DIREITA e NENHUM. Dependendo de qual direção o usuário rola, um bitmap diferente é aplicado no bitmap atual.

@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
    if (mCurrentScrollDirection.ordinal() == ScrollDirection.NONE.ordinal()) {
        if (distanceX > 0) {
            mCurrentScrollDirection = ScrollDirection.LEFT;
        } else {
            mCurrentScrollDirection = ScrollDirection.RIGHT;
        }
    }
    mTouchX = (int) e2.getX();
    overlayBitmaps(mTouchX);
    return false;
}

private void overlayBitmaps(int coordinateX) {

    switch (mCurrentScrollDirection) {
        case NONE: {
            //do nothing here
            break;
        }
        case LEFT: {
            overlayNextBitmap(coordinateX);
            break;
        }
        case RIGHT: {
            overlayPreviousBitmap(coordinateX);
            break;
        }
    }
}

private void overlayPreviousBitmap(int coordinateX) {
    mImageCanvas.save();

    Bitmap OSBitmap = Bitmap.createBitmap(mCurrentBitmap, coordinateX, 0, mCurrentBitmap.getWidth() - coordinateX, mCurrentBitmap.getHeight());
    mImageCanvas.drawBitmap(OSBitmap, coordinateX, 0, null);

    Bitmap FSBitmap = Bitmap.createBitmap(mPreviousBitmap, 0, 0, coordinateX, mCurrentBitmap.getHeight());
    mImageCanvas.drawBitmap(FSBitmap, 0, 0, null);

    mImageCanvas.restore();

    mCapturedImageView.setImageDrawable(new BitmapDrawable(getResources(), mResultBitmap));
}

private void overlayNextBitmap(int coordinateX) {
    mImageCanvas.save();

    Bitmap OSBitmap = Bitmap.createBitmap(mCurrentBitmap, 0, 0, coordinateX, mCurrentBitmap.getHeight());
    mImageCanvas.drawBitmap(OSBitmap, 0, 0, null);

    Bitmap FSBitmap = Bitmap.createBitmap(mNextBitmap, coordinateX, 0, mCurrentBitmap.getWidth() - coordinateX, mCurrentBitmap.getHeight());
    mImageCanvas.drawBitmap(FSBitmap, coordinateX, 0, null);

    mImageCanvas.restore();

    mCapturedImageView.setImageDrawable(new BitmapDrawable(getResources(), mResultBitmap));
}

Isso funciona muito bem, eu só não testei em dispositivos de pouca memória, considerando que não consegui encontrar muitos:)

Para verificar a referência completa do código este link para fora. É minha própria biblioteca, onde você pode capturar imagens, aplicar filtros e obter um retorno de chamada para a atividade de chamada. Ainda está em andamento.

    
por PunK _l_ RuLz 19.07.2016 / 12:30
fonte
0

Uma solução alternativa:

Renderize a imagem em um SurfaceTexture. Use esse SurfaceTexture como uma entrada de textura OpenGL "GL_OES_EGL_image_external" em um shader de fragmento OpenGL. Desenhe um quad de tela inteira usando este shader de fragmento em um SurfaceTexture secundário. Renderize o SurfaceTexture secundário em um TextureView.

Conseguir que esta primeira parte funcione é a parte difícil. Depois de conseguir isso, você poderá aplicar diferentes shaders às imagens, mas não alternar entre elas, como mostrado na figura. Para adicionar uma troca suave entre imagens, renderize dois shaders de fragmento diferentes no SurfaceTexture secundário, usando GL_SCISSOR para dividir a tela ao meio, dependendo de um valor de deslocamento.

A principal vantagem deste método é que ele usará significativamente menos memória. O bitmap pode ser carregado uma vez e depois de renderizado no SurfaceTexture uma vez, pode ser descartado.

Uma vantagem secundária deste método é que filtros mais complicados podem ser aplicados, e que com um pouco de trabalho extra, você poderá renderizar vídeos também.

Se você estiver interessado em ver uma implementação dessa técnica (que também inclui filtragem de vídeo), confira o Kfilter

    
por isaac.udy 25.01.2018 / 11:38
fonte