Browse Source

Cropper and overlay improvements, some minor fixes.

tags/v1.4.4
Ivan Bravo Bravo 9 months ago
parent
commit
63615de193

+ 2
- 2
src/components/Nudity/PhotoRun.vue View File

@@ -239,8 +239,7 @@ export default {

<style lang="scss" scoped>
.photo-run {
@apply relative;
@apply bg-cover bg-center border-2 border-dark-100;
@apply relative border-2 border-dark-100;
background-image: url('~@/assets/images/curls.png'); /* Background pattern from Toptal Subtle Patterns */
min-height: 512px;
transition: all .15s linear;
@@ -268,6 +267,7 @@ export default {

.run__preview {
@apply absolute opacity-0 left-0 right-0 top-0 bottom-0 z-10;
@apply bg-cover bg-center;
transition: all .3s linear;
}
}

+ 5
- 5
src/components/Settings/Preference.vue View File

@@ -2,7 +2,7 @@
<section class="box box--items">
<div class="box__content">
<box-item :description="`Value: ${currentValue.size}`" :label="`${label} size`">
<VueSlider v-model="currentValue.size" :min="0.3" :max="2" :interval="0.05" />
<VueSlider v-model="currentValue.size" :min="min" :max="max" :interval="0.05" />
</box-item>

<box-item
@@ -39,8 +39,8 @@
<VueSlider
v-model="randomizeRange"
:min-range="0.05"
:min="minRange"
:max="maxRange"
:min="min"
:max="max"
:interval="0.05" />
</box-item>
</div>
@@ -59,11 +59,11 @@ export default {
type: String,
required: true,
},
minRange: {
min: {
type: Number,
default: 0.3,
},
maxRange: {
max: {
type: Number,
default: 2,
},

+ 33
- 26
src/components/Settings/SettingsPreferences.vue View File

@@ -1,25 +1,25 @@
<template>
<div class="c-preferences">
<section v-show="currentValue.advanced.transformMode !== 'import-maskfin'" class="box box--items">
<section v-show="currentValue.advanced.transformMode !== 'import-maskfin'" id="preferences-runs" class="box box--items">
<div class="box__header">
<h2 class="title">
Per run.
</h2>
<h3 class="subtitle">
Customize what will happen in each transformation.
Customize what will happen when you nudify.
</h3>
</div>

<div class="box__content">
<box-item
label="Runs."
description="Number of times the photo will be transformed.">
description="Number of times the photo will be nudified.">
<input v-model="currentValue.body.executions" type="number" min="1" class="input">
</box-item>

<box-item
label="Randomize."
description="Random body preferences will be set at each run.">
description="Set random body preferences at each run.">
<select v-model="currentValue.body.randomize" class="input">
<option :value="true">
Enabled
@@ -33,7 +33,7 @@
<box-item
v-show="!currentValue.body.randomize"
label="Progressive."
:description="`Body preferences will increase their value ${currentValue.body.progressive.rate} at each run.`">
:description="`Body preferences will increase ${currentValue.body.progressive.rate} at each run.`">
<select v-model="currentValue.body.progressive.enabled" class="input">
<option :value="true">
Enabled
@@ -45,8 +45,8 @@
</box-item>

<box-item
v-show="!currentValue.body.randomize"
label="Progressive Rate."
v-show="!currentValue.body.randomize && currentValue.body.progressive.enabled"
label="Progressive rate."
:description="`Value: ${currentValue.body.progressive.rate}`">
<VueSlider v-model="currentValue.body.progressive.rate" :min="0.1" :max="0.9" :interval="0.05" />
</box-item>
@@ -54,7 +54,7 @@
</section>

<!-- Boobs -->
<Preference v-model="currentValue.body.boobs" label="Boobs" />
<Preference id="preferences-body" v-model="currentValue.body.boobs" label="Boobs" />

<!-- Areola -->
<Preference v-model="currentValue.body.areola" label="Areola" />
@@ -63,13 +63,13 @@
<Preference v-model="currentValue.body.nipple" label="Nipple" />

<!-- Vagina -->
<Preference v-model="currentValue.body.vagina" label="Vagina" :max-range="1.5" />
<Preference v-model="currentValue.body.vagina" label="Vagina" :max="1.5" />

<!-- Pubic Hair -->
<Preference v-model="currentValue.body.pubicHair" label="Pubic Hair" :min-range="0" />
<Preference v-model="currentValue.body.pubicHair" label="Pubic Hair" :min="0" />

<!-- Advanced -->
<section class="box box--items">
<section id="preferences-advanced" class="box box--items">
<div class="box__header">
<h2 class="title">
Advanced.
@@ -81,6 +81,7 @@

<div class="box__content">
<box-item
id="preferences-advanced-scale"
label="Scale method."
description="Method to scale the photo to 512x512">
<select v-model="currentValue.advanced.scaleMode" class="input">
@@ -106,8 +107,22 @@
</box-item>

<box-item
label="Transform method."
description="Transformation method, only recommended for advanced users.">
id="preferences-advanced-color"
label="Color transfer."
description="Use a experimental algorithm to try to recover the original colors of the photo.">
<select v-model="currentValue.advanced.useColorTransfer" class="input">
<option :value="true">
Enabled
</option>
<option :value="false">
Disabled
</option>
</select>
</box-item>

<box-item
label="Transformation method."
description="Advanced users. Indicates additional options for transformation.">
<select v-model="currentValue.advanced.transformMode" class="input">
<option value="normal">
Nudify
@@ -120,28 +135,20 @@
</option>
</select>
</box-item>

<box-item
label="Color transfer."
description="Use a experimental algorithm to try to recover the original colors of the photo.">
<select v-model="currentValue.advanced.useColorTransfer" class="input">
<option :value="true">
Enabled
</option>
<option :value="false">
Disabled
</option>
</select>
</box-item>
</div>
</section>
</div>
</template>

<script>
import { tutorial } from '~/modules'
import { VModel } from '~/mixins'

export default {
mixins: [VModel],

mounted() {
tutorial.preferences()
},
}
</script>

+ 11
- 7
src/modules/nudify/photo.js View File

@@ -152,14 +152,18 @@ export class Photo {
get scaleMode() {
const { scaleMode } = this.preferences.advanced

if (scaleMode === 'cropjs' && !this.fileCrop.exists) {
// no crop, automatically rescale for convenience
return 'auto-rescale'
}
if (scaleMode === 'cropjs') {
if (!this.canModify) {
this.consola.debug('Wanted to use the cropper but we cannot modify.')
return 'auto-rescale'
}

if ((scaleMode === 'cropjs' || scaleMode === 'overlay') && !this.canModify) {
// this file can't be modified
return 'auto-rescale'
if (!this.fileCrop.exists) {
this.consola.debug('Wanted to use the cropper but the file does not exist.')

// no crop, automatically rescale for convenience
return 'auto-rescale'
}
}

return scaleMode

+ 3
- 2
src/modules/services/logrocket.js View File

@@ -71,7 +71,7 @@ class LogRocketService extends BaseService {
},
},
dom: {
isEnabled: settings.telemetry?.dom || true,
isEnabled: settings.telemetry?.dom,
baseHref: $provider.ngrok.getAddress() || nucleus.urls?.internal?.cdn,
},
}
@@ -85,7 +85,7 @@ class LogRocketService extends BaseService {
try {
LogRocket.init(this.accessToken, this.config)

LogRocket.identify(settings.payload.user, {
LogRocket.identify(settings.user, {
settings: settings.payload,
})

@@ -94,6 +94,7 @@ class LogRocketService extends BaseService {

consola.info('LogRocket enabled!')
consola.debug(`Access Token: ${this.accessToken}`)
consola.debug(this.config)
} catch (err) {
consola.warn('LogRocket setup failed!', err)
}

+ 17
- 13
src/modules/services/nucleus.js View File

@@ -10,7 +10,7 @@
import { isNil } from 'lodash'
import axios from 'axios'
import { BaseService } from './base'
import { settings } from '../system'
import { settings } from '../system/settings'
import { Consola } from '../consola'

const { system } = $provider
@@ -36,6 +36,19 @@ export class NucleusService extends BaseService {
return !isNil(this.appId)
}

/**
* @type {Object}
*/
get config() {
return {
disableTracking: false,
disableErrorReports: true,
userId: settings.user,
version: process.env.npm_package_version,
persist: true,
}
}

/**
* Setup service
*/
@@ -47,28 +60,19 @@ export class NucleusService extends BaseService {
try {
const Nucleus = require('nucleus-nodejs')

// nucleus configuration
const config = {
disableTracking: settings.telemetry.enabled === false,
disableErrorReports: true,
userId: settings.user,
version: process.env.npm_package_version,
persist: true,
}

Nucleus.init(this.appId, config)
Nucleus.init(this.appId, this.config)

Nucleus.appStarted()

this.service = Nucleus
this.enabled = true

await this.fetchData()
setInterval(this.fetchData.bind(this), 15 * 60 * 1000)

this.enabled = true

consola.info('Nucleus enabled!')
consola.debug(`App ID: ${this.appId}`)
consola.debug(this.config)
} catch (err) {
consola.warn('Nucleus setup failed!', err)
}

+ 1
- 0
src/modules/services/rollbar.js View File

@@ -104,6 +104,7 @@ class RollbarService extends BaseService {

consola.info('Rollbar started!')
consola.debug(`Access Token: ${this.accessToken}`)
consola.debug(this.config)
} catch (err) {
consola.warn('Rollbar setup failed!', err)
}

+ 1
- 1
src/modules/system/achievements.js View File

@@ -33,7 +33,7 @@ export const achievements = {
html: 'You\'re gonna have a bad time.',
toast: true,
position: 'bottom-end',
timer: 6000,
timer: 15000,
timerProgressBar: true,
})


+ 73
- 0
src/modules/tutorial.js View File

@@ -83,4 +83,77 @@ export const tutorial = {

localStorage.setItem('tutorial.upload', 'true')
},

badtime() {
const seen = localStorage.getItem('tutorial.badtime')

if (!isNil(seen)) {
return
}

const intro = introJs()

intro.setOptions({
showBullets: false,
overlayOpacity: 0.7,
steps: [
{
element: '#badtime',
intro: 'You have unlocked the BadTime easter-egg! Use the arrows on your keyboard to play while your photos are nudified in the background.',
},
],
})

intro.start()

localStorage.setItem('tutorial.badtime', 'true')
},

preferences() {
const seen = localStorage.getItem('tutorial.preferences')

if (!isNil(seen)) {
return
}

const intro = introJs()

intro.setOptions({
showBullets: false,
overlayOpacity: 0.7,
steps: [
{
intro: 'Photo preferences are an important part of DreamTime, each photo has its set of preferences with which it works best. Let me give you some information.',
},

{
element: '#preferences-runs',
intro: 'In this section you can find the options to execute several transformations in the same photo. The best way to take advantage of them is to increase the number of runs and activate the Randomize or Progressive option so that each run has different preferences and you can save the result that you like best.',
},

{
element: '#preferences-body',
intro: 'In this section you can customize the size of the body parts, this depends entirely on your tastes!',
},

{
element: '#preferences-advanced-scale',
intro: 'This option can dramatically increase or decrease the quality of the result. If you come from DeepNude, the Manual Crop option will be the one you feel most comfortable with, but we recommend you experiment with the other options and find the ideal one for your photo.',
},

{
element: '#preferences-advanced-color',
intro: 'Activating this option will apply an algorithm that could restore the original colors of the photo, it does not always work but it is worth trying.',
},

{
intro: 'That\'s all for now, as we said before we recommend you experiment with these preferences, with a little practice you will start creating amazing nudes!',
},
],
})

intro.start()

localStorage.setItem('tutorial.preferences', 'true')
},
}

+ 1
- 0
src/pages/dreamnet.vue View File

@@ -106,6 +106,7 @@ export default {
@apply absolute h-full w-full;
@apply flex items-center justify-center;
@apply px-6 bg-black-80 opacity-0;
backdrop-filter: blur(6px);
}

.header__content {

+ 3
- 1
src/pages/games/badtime.vue View File

@@ -1,6 +1,7 @@
<template>
<div class="badtime">
<iframe
id="badtime"
src="https://badtime.dreamnet.tech"
name="badtime"
scrolling="no"
@@ -12,11 +13,12 @@
</template>

<script>
import { events } from '~/modules'
import { events, tutorial } from '~/modules'

export default {
mounted() {
this.unlock()
tutorial.badtime()
},

methods: {

+ 1
- 1
src/pages/nudify/_id.vue View File

@@ -159,6 +159,6 @@ export default {
}

.nudify__content {
@apply flex-1;
@apply flex-1 overflow-x-auto;
}
</style>

+ 29
- 35
src/pages/nudify/_id/crop.vue View File

@@ -19,11 +19,7 @@

<div class="box__content">
<p>
This tool allows you to manually crop the photo so that the selected area is resized to 512x512
</p>

<p>
<font-awesome-icon icon="mouse-pointer" /> Move the photo by dragging it with the mouse, you can zoom in or out using the mouse wheel.
This tool allows you to manually select the area you want to be cropped from the photo and resized.
</p>
</div>
</section>
@@ -31,19 +27,25 @@
<section class="box">
<div class="box__header">
<h2 class="title">
<font-awesome-icon icon="question-circle" /> How to obtain better results?
<font-awesome-icon icon="mouse-pointer" /> Commands
</h2>
</div>

<div class="box__content">
<p>
<ul>
<li>Only one person should appear in the photo.</li>
<li>The person is standing in a straight position without crossing arms or legs.</li>
<li>The person is looking towards the camera.</li>
<li>The person wears light clothes. Bikinis work better.</li>
<li>The person's body is visible and unobstructed.</li>
</ul>
- Increase or decrease the zoom with the mouse wheel.
</p>

<p>
- Click and drag somewhere in the photo to create the crop box.
</p>

<p>
- You can move the crop box by dragging it.
</p>

<p>
- You can increase or decrease the size of the cropbox by dragging any of the anchor points in the corners.
</p>
</div>
</section>
@@ -51,13 +53,13 @@
<section class="box">
<div class="box__header">
<h2 class="title">
<font-awesome-icon icon="exclamation-triangle" /> Use at your own risk.
<font-awesome-icon icon="exclamation-triangle" /> Warning.
</h2>
</div>

<div class="box__content">
<p>
This tool can dramatically decrease the quality of the photo, its use is not recommended.
This tool can dramatically decrease the quality of some photos. (blurry photos)
</p>
</div>
</section>
@@ -66,8 +68,6 @@
</template>

<script>
import Cropper from 'cropperjs'

export default {
computed: {
photo() {
@@ -87,28 +87,20 @@ export default {
/**
*
*/
create() {
async create() {
const Cropper = require('cropperjs')

this.photo.cropper = new Cropper(this.$refs.cropCanvas, {
viewMode: 0,
dragMode: 'move',
cropBoxMovable: false,
cropBoxResizable: false,
toggleDragModeOnDblclick: false,
minCropBoxWidth: 512,
minCropBoxHeight: 512,
maxCropBoxWidth: 512,
maxCropBoxHeight: 512,
aspectRatio: 1,
modal: true,
guides: true,
highlight: true,
autoCropArea: 1,
wheelZoomRatio: 0.03,
wheelZoomRatio: 0.05,
})

this.reload()
},

/**
*
*/
async reload() {
await this.photo.syncEditor()
this.cropper.replace(this.photo.fileInput.path)
@@ -122,6 +114,10 @@ export default {
@apply flex h-full;
}

.cropper__crop {
@apply w-3/4 h-full;
}

.cropper__help {
@apply w-1/4 ml-4;

@@ -142,7 +138,5 @@ export default {
}
}

.cropper__crop {
@apply flex-1 h-full;
}

</style>

+ 4
- 2
src/pages/nudify/_id/editor.vue View File

@@ -5,8 +5,7 @@
</template>

<script>
import ImageEditor from 'tui-image-editor'
import { blackTheme } from '~/modules/editor.theme'


export default {
computed: {
@@ -24,6 +23,9 @@ export default {
*
*/
async create() {
const ImageEditor = require('tui-image-editor')
const { blackTheme } = require('~/modules/editor.theme')

this.photo.editor = new ImageEditor(this.$refs.imageEditor, {
includeUI: {
loadImage: {

+ 31
- 22
src/pages/nudify/_id/overlay.vue View File

@@ -19,15 +19,37 @@

<div class="box__content">
<p>
This tool allows you to select which area of the photo you want to cut, transform and then restore to the original photo.
This tool allows you to manually select the area you want to be cropped, nudified and then restored to the original photo.
</p>

<p>
It is perfect for big photos where you just want to transform a specific area but you don't want to lose everything else.
</p>
</div>
</section>

<section class="box">
<div class="box__header">
<h2 class="title">
<font-awesome-icon icon="mouse-pointer" /> Commands
</h2>
</div>

<div class="box__content">
<p>
- Increase or decrease the zoom with the mouse wheel.
</p>

<p>
- Click and drag somewhere in the photo to create the crop box.
</p>

<p>
<font-awesome-icon icon="mouse-pointer" /> Move the photo by dragging it with the mouse, you can zoom in or out using the mouse wheel.
- You can move the crop box by dragging it.
</p>

<p>
- You can increase or decrease the size of the cropbox by dragging any of the anchor points in the corners.
</p>
</div>
</section>
@@ -35,18 +57,13 @@
<section class="box">
<div class="box__header">
<h2 class="title">
<font-awesome-icon icon="question-circle" /> How to obtain better results?
<font-awesome-icon icon="exclamation-triangle" /> Warning.
</h2>
</div>

<div class="box__content">
<p>
<ul>
<li>The person is standing in a straight position without crossing arms or legs.</li>
<li>The person is looking towards the camera.</li>
<li>The person wears light clothes. Bikinis work better.</li>
<li>The person's body is visible and unobstructed.</li>
</ul>
This tool can dramatically decrease the quality of some photos. (blurry photos)
</p>
</div>
</section>
@@ -56,7 +73,6 @@

<script>
import { round } from 'lodash'
import Cropper from 'cropperjs'

export default {
data: () => ({
@@ -78,6 +94,8 @@ export default {
*
*/
async create() {
const Cropper = require('cropperjs')

this.$refs.cropCanvas.addEventListener('crop', () => {
const data = this.cropper.getData()

@@ -91,25 +109,16 @@ export default {

this.cropper = new Cropper(this.$refs.cropCanvas, {
viewMode: 1,
dragMode: 'move',
cropBoxMovable: false,
cropBoxResizable: false,
toggleDragModeOnDblclick: false,
minCropBoxWidth: 512,
minCropBoxHeight: 512,
maxCropBoxWidth: 512,
maxCropBoxHeight: 512,
aspectRatio: 1,
modal: true,
guides: true,
highlight: true,
autoCropArea: 1,
wheelZoomRatio: 0.05,
})

this.reload()
},

/**
*
*/
async reload() {
await this.photo.syncEditor()
this.cropper.replace(this.photo.fileInput.path)

+ 1
- 1
src/pages/settings/app.vue View File

@@ -13,7 +13,7 @@
Put in Queue
</option>
<option value="go-preferences">
Put in Pending and open preferences
Put in Pending and Open preferences
</option>
</select>
</box-item>

+ 4
- 4
src/pages/settings/folders.vue View File

@@ -8,25 +8,25 @@
<div class="box__content">
<box-item
label="DreamPower"
description="Location of DreamPower (also known as CLI)">
description="Algorithm location.">
<input v-model="currentValue.folders.cli" readonly class="input" title="Change" @click.prevent="changePower">
</box-item>

<box-item
label="Models"
description="Location where the transformed photos will be saved.">
description="Location where all nudified photos will be saved.">
<input v-model="currentValue.folders.models" class="input" readonly title="Change" @click.prevent="changeModels">
</box-item>

<box-item
label="Cropped"
description="Location where the cropped photos will be saved. We recommend selecting a temporary folder.">
description="Location where the cropped and editor photos will be saved before nudifying.">
<input v-model="currentValue.folders.cropped" class="input" readonly title="Change" @click.prevent="changeCropped">
</box-item>

<box-item
label="Masks"
description="Location where the algorithm masks photos will be saved. We recommend selecting a temporary folder.">
description="Location where the algorithm masks photos will be saved.">
<input v-model="currentValue.folders.masks" class="input" readonly title="Change" @click.prevent="changeMasks">
</box-item>
</div>

+ 2
- 2
src/pages/settings/processing.vue View File

@@ -5,7 +5,7 @@
<box-item
v-if="!isMacOS"
label="Device."
description="Device that will be used to transform photos. GPU is faster.">
description="Device that will be used to nudify. GPU is faster.">
<select v-model="currentValue.processing.device" class="input">
<option value="CPU">
CPU
@@ -30,7 +30,7 @@
<box-item
v-if="currentValue.processing.device === 'GPU'"
label="GPU."
description="Graphics card that will be used to transform the photos.">
description="Graphics card used.">
<select v-model="currentValue.processing.gpus[0]" class="input">
<option v-for="(device, index) in $provider.system.graphics" :key="index" :value="index">
{{ device.model }}

Loading…
Cancel
Save