Края овала ShapeDrawable (стиль штриха) обрезаются (Android Studio)

Я новичок в Android Studio и сейчас пытаюсь создать овал (не сплошной, просто обводка) случайного цвета, ширины и размера обводки программно:

        long randomSeedm = System.currentTimeMillis();
        Random random = new Random(randomSeedm);
        int[] color = {R.color.red, R.color.black, .....};

        int ovalWidth = 20 + random.nextInt(100);
        int ovalHeight = 20 + random.nextInt(100);

        ShapeDrawable shape = new ShapeDrawable(new OvalShape());
        shape.setIntrinsicWidth (ovalWidth);
        shape.setIntrinsicHeight (ovalHeight);
        shape.getPaint().setColor(getResources().getColor(color[random.nextInt(6)]));
        shape.getPaint().setStyle(Paint.Style.STROKE);
        shape.getPaint().setStrokeWidth(2+random.nextInt(15));
        shape.getPaint().setAntiAlias(true);

        ImageView oval = new ImageView(this);
        oval.setImageDrawable(shape);

После того, как я поместил ImageView в FrameLayout, который покрывает весь экран:

        FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ovalWidth, ovalHeight);
        left = random.nextInt(frameLayoutWidth - ovalWidth);
        top = random.nextInt(frameLayoutHeight - ovalHeight);
        params.leftMargin = left;
        params.topMargin = top;
        params.gravity = Gravity.TOP + Gravity.LEFT;

        frameLayoutWholeScreen.addView(oval, params);

Результаты очень удовлетворительные (с точки зрения моего начинающего), единственная проблема в том, что края овалов частично обрезаны. Вот некоторые примеры:

Пример 1

1

Пример 2

2

Есть ли какой-нибудь способ избежать порезов?

2 ответа

Вам нужно добавить значение обводки при создании параметров макета кадра.

    int strokeSize = 2 + random.nextInt(15);
    FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ovalWidth + strokeSize, ovalHeight + strokeSize);
    left = random.nextInt(frameLayoutWidth - (ovalWidth + strokeSize));
    top = random.nextInt(frameLayoutHeight - (ovalHeight + strokeSize));
    params.leftMargin = left;
    params.topMargin = top;
    params.gravity = Gravity.TOP + Gravity.LEFT;
    frameLayoutWholeScreen.addView(oval, params);

У нас все еще есть эта проблема с Paint.

Судя по тому, что я проанализировал, кажется, что краска пытается нарисовать обводку на краю изображения (т. е. в начале, конце, верхней или нижней части), имея край (или соответствующие начальную, конечную, верхнюю или нижнюю точки) как средняя точка штриха, в результате чего отображается только половина штриха, а другая половина ширины штриха отображается за пределами представления. Это может быть или не быть неправильным.

Решение: Старайтесь не рисовать краску по краям (т.е. начало, конец, верх или низ) ровно. Уменьшите размер конечных точек.

У меня сработало изменение конечных точек следующим образом: начало + (1.dpToPx), верх + (1.dpToPx), низ - (1.dpToPx), конец - (1.dpToPx).

Другие вопросы по тегам