Soru Kare resmi kırpın - Program aracılığıyla


Bir gün geçmişti ve başarılı olamadım.

API'dan görüntü alıyorum ve aşağıdaki kodu kullanarak bir bitmap dosyasına indiriyorum.

private Bitmap DownloadImage(String URL) 
    {
        Bitmap bitmap = null;
        InputStream in = null;
        try 
        {
            in = OpenHttpConnection(URL);
            bitmap = BitmapFactory.decodeStream(in);
            in.close();
        }
        catch (IOException e1) 
        {
            e1.printStackTrace();
        }
        return bitmap;
    }

    private InputStream OpenHttpConnection(String urlString) throws IOException 
    {
        InputStream in = null;
        int response = -1;

        URL url = new URL(urlString);
        URLConnection conn = url.openConnection();

        if (!(conn instanceof HttpURLConnection))
            throw new IOException("Not an HTTP connection");

        try 
        {
            HttpURLConnection httpConn = (HttpURLConnection) conn;
            httpConn.setAllowUserInteraction(false);
            httpConn.setInstanceFollowRedirects(true);
            httpConn.setRequestMethod("GET");
            httpConn.connect();

            response = httpConn.getResponseCode();
            if (response == HttpURLConnection.HTTP_OK) 
            {
                in = httpConn.getInputStream();
            }
        }
        catch (Exception ex) 
        {
            throw new IOException("Error connecting");
        }
        return in;
    }

Görüntüyü kare olarak alıyorum ve dört köşeyi kırpıp dairesel görüntüye dönüştürmek istiyorum. Elde etmek için herhangi bir yol var mı?

İlgili herhangi bir cevap kabul edilir. Şimdiden teşekkürler .


17
2018-04-01 13:10


Menşei


Kafamın üstünden emin değilim, ama alternatif bir yaklaşım olarak, orijinal görüntünün üstünde boyutlandırılmış delikle bir alfa daire görüntüsü oluşturmak olabileceğini düşünüyorum. Bu, bir daire sınıfıyla çalışmak ve uygun düzenlemeleri yapmakla karşılaştırıldığında ideal değildir, ancak aradığınızı bulamıyorsanız ve hızlı bir çözüme ihtiyacınız varsa bir alternatif. - Jay Snayder


Cevaplar:


public class MainActivity extends Activity {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        // TODO Auto-generated method stub
        super.onCreate(savedInstanceState);
        DrawingView dv = new DrawingView(this);
        setContentView(dv);
    }

    class DrawingView extends View {
        Bitmap bitmap;

        public DrawingView(Context context) {
            super(context);
            bitmap = BitmapFactory.decodeResource(context.getResources(),
                    R.drawable.glossy_overlay);

        }

        @Override
        public void onDraw(Canvas canvas) {
            Paint paint = new Paint();
            // paint.setColor(Color.CYAN);
            canvas.drawBitmap(getclip(), 30, 20, paint);
        }

        public Bitmap getclip() {
            Bitmap output = Bitmap.createBitmap(bitmap.getWidth(),
                    bitmap.getHeight(), Config.ARGB_8888);
            Canvas canvas = new Canvas(output);
            final int color = 0xff424242;
            final Paint paint = new Paint();
            final Rect rect = new Rect(0, 0, bitmap.getWidth(),
                    bitmap.getHeight());

            paint.setAntiAlias(true);
            canvas.drawARGB(0, 0, 0, 0);
            // paint.setColor(color);
            canvas.drawCircle(bitmap.getWidth() / 2,
                    bitmap.getHeight() / 2, bitmap.getWidth() / 2, paint);
            paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
            canvas.drawBitmap(bitmap, rect, rect, paint);
            return output;
        }
    }
}

19
2018-04-01 13:49



Bu kod, her defasında kırpılmış bitmap'i yeniden oluşturacaktır. Sadece kaynak bitmap değiştiğinde kırpılmış çekilebilir bir referans oluşturmak ve daha sonra bunu çizmek için. Aslında, kaynak bitmapine yapılan başvuruyu da kaybedebilirsiniz. Boyayı çizim döngüsünün dışında ayırmak da daha iyidir. - greg7gkb
@ greg7gkb önerisi, zamanım olduğunda gönderimi iyileştirecek - Raghunandan


Bitmap alındıktan sonra RoundedBitmapDrawableFactory üretmek için kullanılabilir RoundedBitmapDrawable itibaren v4 Destek Kitaplığı. o Drawable daha sonra bir uygulamaya uygulanabilir ImageView ya da doğrudan Canvas.

// Create the RoundedBitmapDrawable.
RoundedBitmapDrawable roundDrawable = RoundedBitmapDrawableFactory.create(getResources(), bitmap);
roundDrawable.setCircular(true);

// Apply it to an ImageView.
ImageView imageView = (ImageView)findViewById(R.id.imageView);
imageView.setImageDrawable(roundDrawable);

// Alternatively, draw it to an canvas (e.g. in onDraw where a Canvas is available).
// setBounds since there's no View handling size and positioning.
roundDrawable.setBounds(left, top, right, bottom);
roundDrawable.draw(canvas);

16
2018-01-26 20:35



Çok teşekkürler Godfrey, bu cevap en basit ve en iyi cevaptır. Bu kabul edilen cevap olmalı! - JamisonMan111
çok teşekkür ederim, çok faydalı @Godfrey Duke - Shruti


bitmap üzerinde daire çizmek için işlev darbesini kullanın ve ardından daire içine alınmış bitmapi görüntüye ayarlayın

public static Bitmap getclip(Bitmap bitmap) {
    Bitmap output = Bitmap.createBitmap(bitmap.getWidth(),
            bitmap.getHeight(), Config.ARGB_8888);
    Canvas canvas = new Canvas(output);

    final Paint paint = new Paint();
    final Rect rect = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight());

    paint.setAntiAlias(true);
    canvas.drawARGB(0, 0, 0, 0);
    canvas.drawCircle(bitmap.getWidth() / 2, bitmap.getHeight() / 2,
            bitmap.getWidth() / 2, paint);
    paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
    canvas.drawBitmap(bitmap, rect, rect, paint);
    return output;
}

14
2018-05-18 08:20



Büyük işlev, ama bu satırı ne yapar: paint.setXfermode (yeni PorterDuffXfermode (Mode.SRC_IN)); - bebosh
@bebosh, bu bitmap için çizim modunu ayarlar (bkz. ssp.impulsetrain.com/porterduff.html) ya da neden bu yönteme yapılan çağrının gerekli olduğunu soruyor musunuz? - greg7gkb
Bu özel yöntem hatasız çalışır, ancak yatay bir oval görüntü oluşturur. RoundedBitmapDrawableFactory kullanarak, sadece FYI mükemmel bir daire oluşturur. - JamisonMan111


Roman Nurik, gölgelendiricilerin özel bir çekilebilirlikle, böyle şeyleri yapmak için çok doğrudan kullanılmasını önermektedir.

Oval bir görüntü oluşturmak ve kendimi test etmek için kodu biraz değiştirdim. Etki ve performans gerçekten iyi:

public  class StreamDrawable extends Drawable {
private static final boolean USE_VIGNETTE = true;

private final RectF mRect = new RectF();
private final BitmapShader mBitmapShader;
private final Paint mPaint;
private final int mMargin;

public StreamDrawable(Bitmap bitmap, int margin) {

    mBitmapShader = new BitmapShader(bitmap,
            Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);

    mPaint = new Paint();
    mPaint.setAntiAlias(true);
    mPaint.setShader(mBitmapShader);

    mMargin = margin;
}

@Override
protected void onBoundsChange(Rect bounds) {
    super.onBoundsChange(bounds);
    mRect.set(mMargin, mMargin, bounds.width() - mMargin, bounds.height() - mMargin);

    if (USE_VIGNETTE) {
        RadialGradient vignette = new RadialGradient(
                mRect.centerX(), mRect.centerY() * 1.0f / 0.7f, mRect.centerX() * 1.3f,
                new int[] { 0, 0, 0x7f000000 }, new float[] { 0.0f, 0.7f, 1.0f },
                Shader.TileMode.CLAMP);

        Matrix oval = new Matrix();
        oval.setScale(1.0f, 0.7f);
        vignette.setLocalMatrix(oval);

        mPaint.setShader(
                new ComposeShader(mBitmapShader, vignette, PorterDuff.Mode.SRC_OVER));
    }
}

@Override
public void draw(Canvas canvas) {
    canvas.drawOval(mRect, mPaint);
}

@Override
public int getOpacity() {
    return PixelFormat.TRANSLUCENT;
}

@Override
public void setAlpha(int alpha) {
    mPaint.setAlpha(alpha);
}

@Override
public void setColorFilter(ColorFilter cf) {
    mPaint.setColorFilter(cf);
}
}

2
2017-07-04 19:13





Bu sadece xml ile yapılabilir, lütfen cevabımı buraya bakın: https://stackoverflow.com/a/18287979/665930

<RelativeLayout
            android:id="@+id/icon_layout"
            android:layout_width="@dimen/icon_mask"
            android:layout_height="@dimen/icon_mask"
            android:layout_alignParentLeft="true"
            android:layout_alignParentTop="true" >

            <ImageView
                android:id="@+id/icon"
                android:layout_width="@dimen/icon"
                android:layout_height="@dimen/icon"
                android:layout_centerInParent="true"
                android:scaleType="fitXY" >
            </ImageView>

            <ImageView
                android:id="@+id/icon_mask"
                android:layout_width="@dimen/icon_mask"
                android:layout_height="@dimen/icon_mask"
                android:layout_centerInParent="true"
                android:background="@drawable/circle"
                android:scaleType="fitXY" >
            </ImageView>


 </RelativeLayout>


<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="oval" >
    <gradient android:startColor="#00FFFFFF" android:endColor="#00FFFFFF"
        android:angle="270"/>
     <stroke android:width="10dp" android:color="#FFAAAAAA"/>

0
2017-08-17 11:02





Yukarıdaki çözümleri denedim ama hiçbiri benim için iyi çalışmadı. Bunun nedeni telefon kameramın kare görüntü almaması, ancak sadece dikdörtgen görüntüleri olmamasıdır. Bu yüzden, @actsai çözümünde her zaman küçük boyutu almak ve görüntüyü bir daire içinde kırpmak için bazı değişiklikler yapıyorum:

public static Bitmap getBitmapClip(Bitmap bitmap) {
    int maxLenth = bitmap.getWidth() <= bitmap.getHeight() ? bitmap.getWidth() : bitmap.getHeight();
    Bitmap output = Bitmap.createBitmap(maxLenth,
            maxLenth, Bitmap.Config.ARGB_8888);
    Canvas canvas = new Canvas(output);

    final Paint paint = new Paint();
    final Rect rect = new Rect(0, 0, maxLenth, maxLenth);

    paint.setAntiAlias(true);
    canvas.drawARGB(0, 0, 0, 0);
    canvas.drawCircle(maxLenth / 2, maxLenth / 2,
            maxLenth / 2, paint);
    paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
    canvas.drawBitmap(bitmap, rect, rect, paint);
    return output;
}

ImageView'ımı yeni bitmap ile doldurmak için aşağıdaki ölçek özelliğini kullandım:

<ImageView
    android:id="@+id/iv_photo"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_gravity="center"
    android:scaleType="fitXY" />

0
2018-06-19 15:24