Перейти к содержимому

Поиск по сайту

Результаты поиска по тегам 'изображение'.

  • Поиск по тегам

    Введите теги через запятую.
  • Поиск по автору

Тип публикаций


Блоги

  • Робот Байт
  • Fingercomp's Playground
  • 1Ridav' - блог
  • Totoro Cookies
  • Блог cyber01
  • IncluderWorld
  • KelLiN' - блог
  • Крутой блог
  • eutomatic blog
  • Programist135 Soft
  • Сайт в сети OpenNet
  • PieLand
  • Очумелые ручки
  • Блог недоблоггера
  • В мире Майнкрафт
  • LaineBlog
  • Квантовый блог
  • Блог qwertyMAN'а
  • some blog name
  • Дача Игоря
  • Путешествия Xytabich'а
  • Рецепты программирования
  • Шкодим по крупному
  • 123
  • mineOS и её удивительный мир
  • Поляна говнокода Bumer 32

Форумы

  • Программирование
    • Программы
    • База знаний
    • Разработчикам
    • Вопросы
  • Игровой раздел
    • Игровые серверы
    • Моды и плагины
    • Жалобы
    • Ивенты и конкурсы
    • Файлы
  • Общение
    • Задать вопрос
    • Обратная связь
    • Беседка
    • Шкатулка
  • Технический раздел
    • Корзина

Группы продуктов

Нет результатов для отображения.


Искать результаты в...

Искать результаты, которые...


Дата создания

  • Начать

    Конец


Последнее обновление

  • Начать

    Конец


Фильтр по количеству...

Зарегистрирован

  • Начать

    Конец


Группа


AIM


MSN


ICQ


Yahoo


Jabber


ВКонтакте


Город


Интересы

Найдено 4 результата

  1. Уже давно в майнкрафте существует задача: создать библиотеку или программу, которая могла бы отрисовать произвольную картинку. Это нужно в самых разных сценариях: чтобы написать веб-браузер (или, например, приложение-клиент соцсети), показать на здании свой логотип, или для журнального столика в отеле. ——— Что же мешает в OpenComputers просто считать данные картинки и её отрисовать? Разнообразие форматов и настроек. На многих сайтах можно одновременно найти PNG, WebP и JPEG; последние два формата подразумевают сжатие с возможными потерями и в этом отношении очень настраиваются. Соответственно, программе надо с десяток разных модулей/путей кода, чтобы декодировать что угодно — или придётся зависеть от какого-нибудь внешнего конвертера изображений. Разрешение мониторов OC не соответствует размерам стандартных картинок. У мониторов третьего уровня 160x50 знакомест (которые разбиваются на два квадратика в высоту) и всего 256 цветов в палитре. Декодирование целой картинки через виртуальную машину Lua подтормаживает (а без декодирования не получится её даже уменьшить), особенно когда приходится делать паузы для сборщика мусора. Постоянная замена цветов и отрисовка по одному пикселю тормозит уже за счёт ограничений видеокарты в моде. Пункту 4 можно противодействовать с помощью DoubleBuffering от @ECS, пункт 2 требует какого-то алгоритма уменьшения картинки (если же она слишком мала, то мы можем покрутить разрешение монитора). Что же касается первого и третьего... сразу напрашивается идея создать внешнюю библиотеку, которая всем этим бы занималась. На ум приходят несколько вариантов, на чём её можно написать и как интегрировать: Rust (как более безопасный и потенциально быстрый язык) скомпилировать в .dll/.so и подключить к OC, примерно как нативный вариант Lua; Того же подключить из machine.lua; На Scala (тот же язык, на котором написан OpenComputers) сделать патч к самому OpenComputers; ... Уже известно, что первый вариант вызывает мучения (https://computercraft.ru/blogs/entry/666-profiliruem-programmy-pod-oc/) и отсутствие персистентности у компьютеров. Пользователи, очевидно, будут очень рады тому, что программы надо писать из расчёта «всё будет выключаться в произвольные моменты». Поэтому сейчас рассмотрим, как пойти по третьему пути; для простоты компиляции возьмём испытуемым Ocelot Desktop, понимая, что он не очень сильно отличается от OpenComputers. Оказывается, у нас уже есть пример компонента, работающего с данными -- “data card”; основной файл этой карточки можно найти на https://gitlab.com/cc-ru/ocelot/ocelot-brain/-/blob/master/src/main/scala/totoro/ocelot/brain/entity/DataCard.scala. Пример ... object DataCard { val SecureRandomInstance: ThreadLocal[SecureRandom] = new ThreadLocal[SecureRandom]() { override def initialValue: SecureRandom = SecureRandom.getInstance("SHA1PRNG") } class Tier1 extends DataCard { ... override def tier: Tier = Tier.One @Callback(direct = true, limit = 32, doc = """function(data:string):string -- Applies base64 encoding to the data.""") def encode64(context: Context, args: Arguments): Array[AnyRef] = { result(Base64.encodeBase64(check(context, args))) } ... Сразу замечаем, что функции, экспортируемые для использования в Lua, собраны в одном классе и отмечены декоратором @Callback; кроме того, в структуре указываются ещё характеристики компонента (название, «поставщик», уровень и тому подобное). Программируем сами?.. Подумаем теперь над интерфейсом нашей карточки: decode(массив байт) —> обёртка над картинкой (таблица? объект Scala?) обёртка —> ширина, высота обёртка —> получить цвет конкретного пикселя. Раз у нас поддерживается любой формат изображений, то здесь будут четыре канала — R, G, B, A; возможно, методы для первичной обработки изображения? Например, масштабирование. В принципе, этого достаточно, чтобы начать программировать, но попробуем сделать по-другому: попросим нейросеть написать код за нас. В рассуждениях можно будет увидеть, как DeepSeek сомневается, добавлять ли собственно декодирование PNG и других форматов или сделать лишь какой-то сырой, и в итоге он останавливается на втором варианте: Не вполне понятно, в каком именно порядке отдаются цветовые каналы, но это похоже на правду... для какого-то сырого формата, где Lua хватило бы простого выбора байт из строки. Что ж, не будем сдаваться, запросим декодирование популярных форматов. К сожалению, там модель начинает путаться в порядке каналов и в точных импортах, но всё же выдаёт осмысленный код: package totoro.ocelot.brain.entity // Core image processing import com.sksamuel.scrimage.ImmutableImage import com.sksamuel.scrimage.nio.ImageSource import com.sksamuel.scrimage.metadata.ImageMetadata import com.sksamuel.scrimage.implicits._ // For Scala syntactic sugar :cite[2] // Format-specific readers (explicit safe imports) import com.sksamuel.scrimage.webp.WebpWriter import com.sksamuel.scrimage.formats.{GifWriter, JpegWriter, PngWriter} // Error handling import scala.util.{Try, Success, Failure} import totoro.ocelot.brain.entity.machine.{AbstractValue, Arguments, Callback, Context} class ImageDecoder extends /* ... existing entity setup ... */ { @Callback(direct = true, doc = """function(data:string):userdata -- Decodes common formats (PNG/WebP/JPEG/GIF) or raw RGBA""") def decode(context: Context, args: Arguments): Array[AnyRef] = { val data = args.checkByteArray(0) // 1. Attempt standard format decoding via Scrimage :cite[1]:cite[3] Try(ImmutableImage.loader().fromBytes(data)) match { case Success(scrimageImg) => // Convert Scrimage image to raw RGBA format for consistency val rgba = scrimageImg.bytes(PngWriter.NoCompression).take(8) ++ // Store metadata scrimageImg.argbFlatMap(p => Array( ((p >> 16) & 0xFF).toByte, // R ((p >> 8) & 0xFF).toByte, // G (p & 0xFF).toByte, // B ((p >> 24) & 0xFF).toByte // A )) result(new ImageUserdata(scrimageImg.width, scrimageImg.height, rgba)) case Failure(_) => // 2. Fallback to raw format if standard decoding fails if (data.length < 8) throw new IllegalArgumentException("Invalid header") val width = java.nio.ByteBuffer.wrap(data.slice(0, 4)).getInt val height = java.nio.ByteBuffer.wrap(data.slice(4, 8)).getInt if (8 + width*height*4 > data.length) throw new IllegalArgumentException("Invalid pixel data") result(new ImageUserdata(width, height, data.slice(8, data.length))) } } } Программируем сами, да Вооружимся компилятором (для Scala это sbt) и допишем код до нормального состояния. Дадим сначала карточке весёлое название и имя вендора: class ImageCard extends Entity with Environment with DeviceInfo with Tiered { override val node: Node = Network.newNode(this, Visibility.Neighbors) .withComponent("imagine", Visibility.Neighbors) .create() private final lazy val deviceInfo = Map( DeviceAttribute.Class -> DeviceClass.Processor, DeviceAttribute.Description -> "Image decoder card", DeviceAttribute.Vendor -> "ProgramCrafter Individual Enterprises", DeviceAttribute.Product -> "PCI-E Byte-to-Byte Visual-Only Decoder" ) override def getDeviceInfo: Map[String, String] = deviceInfo override def tier: Tier = Tier.Two ... И потом напишем её единственный метод. ... @Callback(direct = false, doc = """function(data:string):userdata -- Decodes an image in common format (PNG/WebP/JPEG/GIF)""") def decode(context: Context, args: Arguments): Array[AnyRef] = { val data = args.checkByteArray(0) val scrimageImg = ImmutableImage.loader().fromBytes(data) result(new ImageUserdata(scrimageImg)) } } class ImageUserdata(var pixels: ImmutableImage) extends AbstractValue { def this() = this(ImmutableImage.create(8, 8)) // For deserialization @Callback(direct = true, doc = "function():number -- Get image width") def getWidth(context: Context, args: Arguments): Array[AnyRef] = result(pixels.width) @Callback(direct = true, doc = "function():number -- Get image height") def getHeight(context: Context, args: Arguments): Array[AnyRef] = result(pixels.height) @Callback(direct = true, limit = 1000000, doc = "function(x:number, y:number):number -- Get ARGB value at specified coordinates, 1-based") def getARGB(context: Context, args: Arguments): Array[AnyRef] = { val x = args.checkInteger(0) - 1 val y = args.checkInteger(1) - 1 if (x < 0 || x >= pixels.width || y < 0 || y >= pixels.height) throw new IllegalArgumentException("coordinates out of bounds") val p = pixels.pixel(x, y) result(p.alpha(), p.red(), p.green(), p.blue()) } @Callback(direct = false, doc = "function(target_width:number, target_height:number):number -- Get a new image scaled appropriately to fit within specified bounds") def fit(context: Context, args: Arguments): Array[AnyRef] = {...} // Serialization private final val PixelTag = "ScrImage" override def load(nbt: NBTTagCompound, workspace: Workspace): Unit = { super.load(nbt, workspace) pixels = ImmutableImage.loader().fromBytes(nbt.getByteArray(PixelTag)) } override def save(nbt: NBTTagCompound): Unit = { super.save(nbt) nbt.setByteArray(PixelTag, pixels.bytes(PngWriter.MaxCompression)) } } Когда всё написанное скомпилируется, обёртка изображения будет поддерживать персистентность, масштабирование, получение размеров и конкретных пикселей картинки. Остаётся пока один нерешённый вопрос: а как этот код будет вызываться? Кормим Оцелота На самом деле добавить новую карточку не очень сложно, достаточно: нарисовать иконку 16x16, поместить в ocelot-desktop/sprites/items прогнать ocelot-desktop/spritepack и положить новый атлас текстур на место старого добавить новую иконку в Icons.scala (в объекте Items) добавить код ImageCard в репозиторий создать подкласс ImageCardItem with CardItem и соответствующую ему Factory зарегать завод в Items.scala Изменения можно посмотреть на https://gitlab.com/ProgramCrafter/ocelot-desktop/-/compare/develop...ac0acb33. Тестируем Окажется ужасно, если наша карточка не будет работать. Поставим её в компьютер и запустим вот такой скрипт: local com = require 'component' local unc = require 'unicode' local img = com.imagine local gpu = com.gpu local function set_halfpixel(x, y, back, fore) local bg, fg = gpu.getBackground(), gpu.getForeground() if bg == fore then gpu.setForeground(back) gpu.set(x, y, unc.char(0x2584)) else if bg ~= back then gpu.setBackground(back) end if fg ~= fore then gpu.setForeground(fore) end gpu.set(x, y, unc.char(0x2580)) end end local filename = (...) or '/home/775251537.0.jpg' local file = io.open(filename, 'rb') local buf = file:read('*a') file:close() local image = assert(img.decode(buf)) local w, h = gpu.getResolution() local image_fit = image.fit(w, (h - 1) * 2) local pts_w, pts_h = image_fit.getWidth(), image_fit.getHeight() io.read() for x = 1, pts_w do for y = 1, pts_h, 2 do local _, r1, g1, b1 = image_fit.getARGB(x, y) local _, r2, g2, b2 = 0,0,0,0 if y + 1 <= pts_h then _,r2,g2,b2 = image_fit.getARGB(x, y + 1) end local top = r1*65536 + g1*256 + b1 local bot = r2*65536 + g2*256 + b2 set_halfpixel(x, (y + 1) // 2, bot, top) end end require'term'.setCursor(1, h) И получим изображение дивана-танка. Требуемые улучшения Проверить, что за библиотека ScrImage, действительно ли она безопаснее или удобнее остальных. (Кажется, что удобнее, ведь она в отличие от javax ImageIO поддерживает WebP.) Сделать так, чтобы открытые картинки потребляли память, потому что сейчас ничто не мешает коду открыть сотню раз по мегабайту. Без этого на сервере такой патч запускать нельзя. Добавить, если не обойдётся вычислительно дорого, фильтры и повороты в интерфейс карточки.
  2. Хочу поделиться с вами конвертером изображений, позволяющим использовать ограниченное пространство мониторов наиболее эффективным образом, а также библиотеками для быстрой отрисовки результата. Поддержка шрифта Брайля позволяет получать изображения размером до 320х200 визуальных точек при физическом ограничении мониторов в 160х50 символов, а алгоритм дизеринга помогает избавиться от визуальных ограничений 256-цветной палитры. Ссылка для загрузки конвертера: https://github.com/IgorTimofeev/OCIFImageConverter/raw/master/out/artifacts/ImageConverter_jar/ImageConverter.jar Команда для установки ПО для отрисовки: pastebin run ng73uZqT Практический пример: Чтобы отобразить картинку на экране, для начала ее необходимо сконвертировать и скопировать любым удобным образом на диск комьютера (напрямую в папку мира, через файловый хостинг и т.п.). В моем случае картинка называется Triss.pic: Затем напишем следующий код или запустим установившуюся программу draw.lua с аргументом "Triss.pic": local args = {...} local image = require("image") local buffer = require("doubleBuffering") -- Очищаем экранный буфер черным цветом buffer.clear(0x0) -- Загружаем и рисуем изображение в буфер buffer.image(1, 1, image.load(args[1])) -- Отрисовываем содержимое буфера в принудительном режиме buffer.draw(true)Результат не заставит себя ждать: Также привожу в качестве демонстрации несколько отрисованных изображений:
  3. Привет всем! Когда я искал библиотеку для создания изображений, отрисовки и т.д. я не нашёл ни одной хорошей библиотеки. Поэтому я написал свою библиотеку, tifAPI! Вам может показаться, что это уже существующее расширение .tif(.tiff), но .tiff расшифровывается как "Tagged Image File Format", а мой - "Text Image Format". А теперь вопросы и ответы (Только на ComputerCraft) Легко, пишем команду pastebin get EnZksdhv installerTIFAPI после скачивания файла пишем следующую команду installerTIFAPI <Папка, в которой будет папка с библиотекой> . Скачивание файлов библиотеки закончиться, когда очиститься экран, и будет надпись "tifAPI has been installed!". Вот Это цвета от 1 до 9 и a, b, c, d, e, f А вот и шпаргалка цветов --[[ a - Номера цветов(colors) b - Сами цвета c - HEX цвет ------------------- a b c 1 0 #F0F0F0 2 1 #F2B233 4 2 #E57FD8 8 3 #99B2F2 16 4 #DEDE6C 32 5 #7FCC19 64 6 #F2B2CC 128 7 #4C4C4C 256 8 #999999 512 9 #4C99B2 1024 a #B266E5 2048 b #3366CC 4096 c #7F664C 8192 d #57A64E 16384 e #CC4C4C 32768 f #191919 ]]-- TifImage - таблица, в которой храниться изображение Да будут.
  4. Хочу представить вам большую библиотеку, предназначенную для работы с изображениями, созданными в нашем Фотошопе. С ее помощью можно манипулировать графикой воистину волшебным образом: изображения можно обрезать, расширять, поворачивать, отражать, инвертировать, изменять их яркость, цветовой тон, насыщенность и добавлять фотофильтры. Разрабатывали мы ее примерно год, содержит она более 1000 строк кода и удовлетворяет практически всем наши требованиям к хорошей графике в OpenComputers, если, конечно, местную графику вообще можно назвать хорошей. Начало работы Прежде всего вам потребуются два файла. Первый обеспечивает основные операции над цветом, позволяет конвертировать цвета из одной схемы в другую, а также сжимать цвета без потери качества. Второй же является самой библиотекой image и дает нам полную свободу творчества. wget https://raw.githubusercontent.com/IgorTimofeev/OpenComputers/master/lib/colorlib.lua lib/colorlib.lua -f wget https://raw.githubusercontent.com/IgorTimofeev/OpenComputers/master/lib/image.lua lib/image.lua -f После загрузки библиотек вы можете подключить image и начинать с ней работать. Далее мы рассмотрим различные методы, с помощью которых мы сможем манипулировать изображениями. Под описанием каждого метода будет картинка и код, демонстрирующие суть работы метода, так что проблем с пониманием возникнуть не должно. local image = require("image") Структура изображений (для общего развития) Методы работы с файлами изображений (загрузка, отрисовка, сохранение) Методы трансформирования изображений (вращение, отражение, обрезание и т.п.) Методы работы с цветом (яркость, насыщенность, тон и т.п.)
×
×
  • Создать...