Skip to content
Toggle navigation
P
Projects
G
Groups
S
Snippets
Help
Rafa Castillo Passols
/
Prototipo-Multimedia
This project
Loading...
Sign in
Toggle navigation
Go to a project
Project
Repository
Issues
0
Merge Requests
0
Pipelines
Wiki
Snippets
Settings
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Commit
54232159
authored
Apr 10, 2025
by
Rafa Castillo Passols
Browse files
Options
_('Browse Files')
Download
Plain Diff
Merge de actualizacionLista
parents
a1d6afbf
38e38526
Hide whitespace changes
Inline
Side-by-side
Showing
9 changed files
with
735 additions
and
233 deletions
lib/modelo/carpeta.dart
lib/modelo/formato.dart
lib/modelo/lista_seleccionables.dart
lib/paginas/pagina_configuracion.dart
lib/paginas/pagina_configuracion_carpeta.dart
lib/paginas/pagina_conversion.dart
lib/paginas/pagina_principal_llena.dart
lib/widgets/carpeta_widget.dart
lib/widgets/seleccionable_widget.dart
lib/modelo/carpeta.dart
View file @
54232159
import
'dart:io'
;
import
'dart:io'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
import
'package:uuid/uuid.dart'
;
import
'archivo.dart'
;
import
'archivo.dart'
;
import
'convertible.dart'
;
import
'convertible.dart'
;
import
'elemento_seleccionable.dart'
;
import
'elemento_seleccionable.dart'
;
...
@@ -7,41 +8,85 @@ import 'formato.dart';
...
@@ -7,41 +8,85 @@ import 'formato.dart';
class
Carpeta
extends
ElementoSeleccionable
{
class
Carpeta
extends
ElementoSeleccionable
{
final
Directory
_directory
;
final
Directory
_directory
;
final
bool
_incluirSubcarpetas
=
false
;
bool
_incluirSubcarpetas
=
false
;
final
List
<
InfoFormato
>
_formatos
;
bool
_open
=
false
;
late
final
List
<
InfoFormato
>
_formatos
;
Directory
get
directory
=>
_directory
;
Directory
get
directory
=>
_directory
;
List
<
InfoFormato
>
get
formatos
=>
List
.
unmodifiable
(
_formatos
);
List
<
InfoFormato
>
get
formatos
=>
List
.
unmodifiable
(
_formatos
);
bool
get
isOpen
=>
_open
;
bool
get
incluyeSubcarpetas
=>
_incluirSubcarpetas
;
Carpeta
({
required
super
.
id
,
required
Directory
directory
}):
Carpeta
({
required
super
.
id
,
required
Directory
directory
}):
_directory
=
directory
,
_formatos
=
[],
_directory
=
directory
,
super
(
nombre:
directory
.
path
.
split
(
'/'
).
last
,
icon:
const
Icon
(
Icons
.
folder_outlined
))
{
_formatos
=
[];
final
archivos
=
directory
.
listSync
(
recursive:
true
,
followLinks:
false
);
for
(
var
a
in
archivos
)
{
Formato
?
f
=
Formato
.
fromExtension
(
a
.
path
.
split
(
"."
).
last
);
if
(
f
!=
null
){
_formatos
.
add
(
InfoFormato
(
formato:
f
,
nombreCarpeta:
directory
.
path
.
split
(
'/'
).
last
,
subCarpeta:
false
));
}
}
}
Carpeta
.
fromList
({
required
super
.
id
,
required
Directory
directory
,
required
List
<
InfoFormato
>
formatos
}):
_directory
=
directory
,
_formatos
=
formatos
,
super
(
nombre:
directory
.
path
.
split
(
'/'
).
last
,
icon:
const
Icon
(
Icons
.
folder_outlined
));
super
(
nombre:
directory
.
path
.
split
(
'/'
).
last
,
icon:
const
Icon
(
Icons
.
folder_outlined
));
InfoFormato
?
getInfoFormato
({
required
Formato
formato
}){
for
(
InfoFormato
i
in
_formatos
){
if
(
i
.
formatoOriginal
==
formato
){
return
i
;
}
}
return
null
;
}
void
setFormatoDestino
(
Formato
original
,
Formato
?
destino
){
final
formatosAlt
=
formatos
.
toList
();
for
(
InfoFormato
i
in
formatosAlt
){
if
(
i
.
formatoOriginal
==
original
){
i
.
formatoDestino
=
destino
;
}
}
}
void
pressOpenClose
(){
_open
=
!
_open
;
}
void
pressIncluirSubcarpetas
(){
_incluirSubcarpetas
=
!
_incluirSubcarpetas
;
}
void
pressAltSeleccionado
(
int
index
){
_formatos
[
index
].
seleccionado
=
!
_formatos
[
index
].
seleccionado
;
}
}
}
class
InfoFormato
{
class
InfoFormato
{
final
bool
_subcarpeta
;
final
bool
_subcarpeta
;
bool
_
seleccionado
;
bool
seleccionado
;
final
Convertible
_conversion
;
final
Convertible
_conversion
;
final
List
<
File
>
_archivos
;
bool
get
subcarpeta
=>
_subcarpeta
;
bool
get
subcarpeta
=>
_subcarpeta
;
bool
get
seleccionado
=>
_seleccionado
;
Convertible
get
conversion
=>
_conversion
;
Convertible
get
conversion
=>
_conversion
;
Formato
get
formatoOriginal
=>
_conversion
.
formatoOriginal
;
Formato
get
formatoOriginal
=>
_conversion
.
formatoOriginal
;
Formato
?
get
formatoDestino
=>
_conversion
.
formatoDestino
;
Formato
?
get
formatoDestino
=>
_conversion
.
formatoDestino
;
List
<
Archivo
>
get
archivos
=>
List
.
unmodifiable
(
_archivos
);
set
seleccionado
(
bool
value
)
=>
_seleccionado
=
value
;
set
formatoDestino
(
Formato
?
destino
)
=>
_conversion
.
formatoDestino
=
destino
;
set
formato
(
Formato
?
destino
)
=>
_conversion
.
formatoDestino
=
destino
;
InfoFormato
({
required
Formato
formato
,
InfoFormato
({
required
Formato
formato
,
required
String
nombreCarpeta
,
required
String
nombreCarpeta
,
required
bool
subCarpeta
,
required
bool
subCarpeta
,
bool
?
seleccionado
,
bool
?
seleccionado
}):
required
List
<
File
>
archivos
}):
_subcarpeta
=
subCarpeta
,
seleccionado
=
seleccionado
??
!
subCarpeta
,
_subcarpeta
=
subCarpeta
,
_seleccionado
=
seleccionado
??
!
subCarpeta
,
_archivos
=
archivos
,
_conversion
=
Convertible
(
id:
const
Uuid
().
v1
(),
nombre:
'
$nombreCarpeta
>
${formato.name}
'
,
_conversion
=
Convertible
(
id:
"null"
,
nombre:
'
$nombreCarpeta
>
${formato.name}
'
,
icon:
Icon
(
Icons
.
find_in_page_outlined
),
formatoOriginal:
formato
);
icon:
Icon
(
Icons
.
find_in_page_outlined
),
formatoOriginal:
formato
);
void
convertir
(){
void
convertir
(){
...
@@ -49,4 +94,10 @@ class InfoFormato {
...
@@ -49,4 +94,10 @@ class InfoFormato {
// TODO: <implement>
// TODO: <implement>
}
}
}
}
@override
bool
operator
==(
Object
other
)
{
if
(
other
is
InfoFormato
)
return
this
.
formatoOriginal
==
other
.
formatoOriginal
;
return
super
==
other
;
}
}
}
\ No newline at end of file
lib/modelo/formato.dart
View file @
54232159
...
@@ -88,12 +88,13 @@ enum Formato {
...
@@ -88,12 +88,13 @@ enum Formato {
}
}
enum
TipoMultimedia
{
enum
TipoMultimedia
{
video
(
Icon
(
Icons
.
movie_creation_outlined
)),
video
(
"Vídeo"
,
Icon
(
Icons
.
movie_creation_outlined
)),
audio
(
Icon
(
Icons
.
music_note_outlined
)),
audio
(
"Audio"
,
Icon
(
Icons
.
music_note_outlined
)),
imagen
(
Icon
(
Icons
.
image_outlined
));
imagen
(
"Imagen"
,
Icon
(
Icons
.
image_outlined
));
final
String
nombre
;
final
Icon
icono
;
final
Icon
icono
;
const
TipoMultimedia
(
this
.
icono
);
const
TipoMultimedia
(
this
.
nombre
,
this
.
icono
);
}
}
enum
Clasificacion
{
enum
Clasificacion
{
...
...
lib/modelo/lista_seleccionables.dart
View file @
54232159
...
@@ -4,6 +4,7 @@ import 'package:uuid/uuid.dart';
...
@@ -4,6 +4,7 @@ import 'package:uuid/uuid.dart';
import
'carpeta.dart'
;
import
'carpeta.dart'
;
import
'elemento_seleccionable.dart'
;
import
'elemento_seleccionable.dart'
;
import
'archivo.dart'
;
import
'archivo.dart'
;
import
'formato.dart'
;
class
ListaSeleccionables
extends
ChangeNotifier
{
class
ListaSeleccionables
extends
ChangeNotifier
{
final
_seleccionables
=
<
ElementoSeleccionable
>[];
final
_seleccionables
=
<
ElementoSeleccionable
>[];
...
@@ -14,15 +15,33 @@ class ListaSeleccionables extends ChangeNotifier {
...
@@ -14,15 +15,33 @@ class ListaSeleccionables extends ChangeNotifier {
notifyListeners
();
notifyListeners
();
}
}
void
actualizaSeleccionable
(
int
indice
,
ElementoSeleccionable
elemento
){
_seleccionables
[
indice
]
=
elemento
;
notifyListeners
();
}
void
addArchivo
(
File
file
)
{
void
addArchivo
(
File
file
)
{
_seleccionables
.
add
(
Archivo
(
id:
"Archivo"
,
_seleccionables
.
add
(
Archivo
(
id:
const
Uuid
().
v1
()
,
file:
file
));
file:
file
));
notifyListeners
();
notifyListeners
();
}
}
void
addCarpeta
(
Directory
directory
){
void
addCarpeta
(
Directory
directory
){
_seleccionables
.
add
(
Carpeta
(
id:
const
Uuid
().
v1
(),
final
newCarpeta
=
Carpeta
(
directory:
directory
));
id:
const
Uuid
().
v1
(),
directory:
directory
);
if
(
newCarpeta
.
formatos
.
isNotEmpty
){
_seleccionables
.
add
(
Carpeta
(
id:
const
Uuid
().
v1
(),
directory:
directory
));
notifyListeners
();
}
}
void
reinsertar
(
int
index
,
ElementoSeleccionable
element
){
_seleccionables
.
insert
(
index
,
element
);
notifyListeners
();
notifyListeners
();
}
}
}
}
\ No newline at end of file
lib/paginas/pagina_configuracion.dart
View file @
54232159
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
import
'package:provider/provider.dart'
;
import
'package:prueba_multimedia/modelo/modelo.dart'
;
import
'package:prueba_multimedia/modelo/modelo.dart'
;
import
'package:prueba_multimedia/paginas/paginas.dart'
;
import
'package:prueba_multimedia/paginas/paginas.dart'
;
class
PaginaConfiguracion
extends
StatefulWidget
{
class
PaginaConfiguracion
extends
StatefulWidget
{
final
ListaSeleccionables
_lista
;
final
int
_indice
;
final
ElementoSeleccionable
_elementoAsociado
;
final
ElementoSeleccionable
_elementoAsociado
;
final
Carpeta
?
_carpeta
;
const
PaginaConfiguracion
({
const
PaginaConfiguracion
({
super
.
key
,
super
.
key
,
required
elementoAsociado
required
ListaSeleccionables
lista
,
}):
_elementoAsociado
=
elementoAsociado
;
required
int
indice
,
required
ElementoSeleccionable
elemento
,
Carpeta
?
carpeta
}):
_lista
=
lista
,
_indice
=
indice
,
_elementoAsociado
=
elemento
,
_carpeta
=
carpeta
;
@override
@override
State
<
PaginaConfiguracion
>
createState
()
=>
_PaginaConfiguracionState
();
State
<
PaginaConfiguracion
>
createState
()
=>
_PaginaConfiguracionState
();
...
@@ -23,10 +31,12 @@ class _PaginaConfiguracionState extends State<PaginaConfiguracion> {
...
@@ -23,10 +31,12 @@ class _PaginaConfiguracionState extends State<PaginaConfiguracion> {
return
Scaffold
(
return
Scaffold
(
appBar:
AppBar
(
appBar:
AppBar
(
title:
RichText
(
title:
RichText
(
maxLines:
1
,
overflow:
TextOverflow
.
ellipsis
,
text:
TextSpan
(
text:
TextSpan
(
children:
[
children:
[
WidgetSpan
(
WidgetSpan
(
child:
Icon
(
_getIcon
()
)
child:
_getIcon
(
)
),
),
TextSpan
(
TextSpan
(
text:
_getShownName
(),
text:
_getShownName
(),
...
@@ -36,19 +46,22 @@ class _PaginaConfiguracionState extends State<PaginaConfiguracion> {
...
@@ -36,19 +46,22 @@ class _PaginaConfiguracionState extends State<PaginaConfiguracion> {
)
)
),
),
),
),
body:
_construirCuerpo
(),
body:
_construirCuerpo
(
widget
.
_lista
),
bottomNavigationBar:
_construirBarraNavegacion
()
bottomNavigationBar:
_construirBarraNavegacion
()
);
);
}
}
Icon
Data
_getIcon
(){
Icon
_getIcon
(){
if
(
widget
.
_elementoAsociado
is
Carpeta
){
if
(
widget
.
_elementoAsociado
is
Carpeta
){
return
Icon
s
.
folder
;
return
Icon
(
Icons
.
folder
)
;
}
}
if
(
widget
.
_elementoAsociado
is
Enlace
){
if
(
widget
.
_elementoAsociado
is
Enlace
){
return
Icon
s
.
link
;
return
Icon
(
Icons
.
link
)
;
}
}
return
Icons
.
insert_drive_file
;
if
(
widget
.
_elementoAsociado
is
Convertible
){
return
(
widget
.
_elementoAsociado
as
Convertible
).
formatoOriginal
.
tipoMultimedia
.
icono
;
}
return
Icon
(
Icons
.
insert_drive_file
);
}
}
String
_getShownName
()
{
String
_getShownName
()
{
...
@@ -58,44 +71,51 @@ class _PaginaConfiguracionState extends State<PaginaConfiguracion> {
...
@@ -58,44 +71,51 @@ class _PaginaConfiguracionState extends State<PaginaConfiguracion> {
return
sb
.
toString
();
return
sb
.
toString
();
}
}
Widget
_construirCuerpo
()
{
Widget
_construirCuerpo
(
ListaSeleccionables
manager
)
{
if
(
widget
.
_elementoAsociado
is
Convertible
){
if
(
widget
.
_elementoAsociado
is
Archivo
){
final
arch
=
widget
.
_elementoAsociado
as
Convertible
;
final
arch
=
widget
.
_elementoAsociado
as
Archivo
;
if
(
_categoriaActiva
==
0
){
if
(
_categoriaActiva
==
0
){
return
PaginaConversion
(
formatoOriginal:
arch
.
formatoOriginal
);
if
(
widget
.
_carpeta
!=
null
){
return
PaginaConversion
.
carpeta
(
lista:
manager
,
indiceArchivo:
widget
.
_indice
,
carpeta:
widget
.
_carpeta
!,
infoFormato:
widget
.
_carpeta
!.
getInfoFormato
(
formato:
arch
.
formatoOriginal
)!,
formatoOriginal:
arch
.
formatoOriginal
);
}
return
PaginaConversion
.
convertible
(
lista:
manager
,
indiceArchivo:
widget
.
_indice
,
elemento:
arch
,
formatoOriginal:
arch
.
formatoOriginal
);
}
}
else
if
(
_categoriaActiva
==
2
){
else
if
(
_categoriaActiva
==
2
||
arch
.
formatoOriginal
.
tipoMultimedia
!=
TipoMultimedia
.
video
){
return
PaginaMetadatos
(
formato:
arch
.
formatoOriginal
);
return
FutureBuilder
(
future:
arch
.
metadatos
,
builder:
(
context
,
snapshot
)
{
return
snapshot
.
hasData
?
PaginaMetadatos
(
metadatos:
snapshot
.
data
!,
formato:
arch
.
formatoOriginal
)
:
CircularProgressIndicator
();
}
);
}
}
else
{
else
{
if
(
arch
.
formatoOriginal
.
tipoMultimedia
==
TipoMultimedia
.
video
){
return
PaginaFotograma
();
return
PaginaFotograma
();
}
// Página de metadatos
return
PaginaMetadatos
(
formato:
arch
.
formatoOriginal
);
}
}
}
}
// Páginas de carpetas y formato de archivo para carpeta
// Páginas de carpetas y formato de archivo para carpeta
// TODO: Carpeta de ejemplo, cargar carpetas de verdad
// TODO: Carpeta de ejemplo, cargar carpetas de verdad
return
PaginaConfiguracionCarpeta
(
formatosCarpeta:
[
return
PaginaConfiguracionCarpeta
(
InfoFormato
(
formato:
Formato
.
jpg
,
lista:
manager
,
nombreCarpeta:
widget
.
_elementoAsociado
.
nombre
,
carpeta:
widget
.
_elementoAsociado
as
Carpeta
,
subCarpeta:
false
,
indice:
widget
.
_indice
archivos:
[]),
);
InfoFormato
(
formato:
Formato
.
mp4
,
nombreCarpeta:
widget
.
_elementoAsociado
.
nombre
,
subCarpeta:
false
,
archivos:
[]),
InfoFormato
(
formato:
Formato
.
tif
,
nombreCarpeta:
widget
.
_elementoAsociado
.
nombre
,
subCarpeta:
true
,
archivos:
[]),
InfoFormato
(
formato:
Formato
.
png
,
nombreCarpeta:
widget
.
_elementoAsociado
.
nombre
,
subCarpeta:
true
,
archivos:
[])
]);
}
}
BottomNavigationBar
?
_construirBarraNavegacion
(){
BottomNavigationBar
?
_construirBarraNavegacion
(){
...
...
lib/paginas/pagina_configuracion_carpeta.dart
View file @
54232159
...
@@ -3,10 +3,21 @@ import 'package:prueba_multimedia/modelo/modelo.dart';
...
@@ -3,10 +3,21 @@ import 'package:prueba_multimedia/modelo/modelo.dart';
import
'package:prueba_multimedia/paginas/paginas.dart'
;
import
'package:prueba_multimedia/paginas/paginas.dart'
;
class
PaginaConfiguracionCarpeta
extends
StatefulWidget
{
class
PaginaConfiguracionCarpeta
extends
StatefulWidget
{
final
ListaSeleccionables
_lista
;
final
List
<
InfoFormato
>
_formatosCarpeta
;
final
List
<
InfoFormato
>
_formatosCarpeta
;
final
int
_indice
;
const
PaginaConfiguracionCarpeta
({
super
.
key
,
required
List
<
InfoFormato
>
formatosCarpeta
}):
final
Carpeta
_carpeta
;
_formatosCarpeta
=
formatosCarpeta
;
PaginaConfiguracionCarpeta
({
super
.
key
,
required
ListaSeleccionables
lista
,
required
int
indice
,
required
Carpeta
carpeta
}):
_lista
=
lista
,
_indice
=
indice
,
_carpeta
=
carpeta
,
_formatosCarpeta
=
carpeta
.
formatos
;
@override
@override
State
<
PaginaConfiguracionCarpeta
>
createState
()
=>
_PaginaConfiguracionCarpetaState
();
State
<
PaginaConfiguracionCarpeta
>
createState
()
=>
_PaginaConfiguracionCarpetaState
();
...
@@ -21,7 +32,7 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
...
@@ -21,7 +32,7 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
@override
@override
void
initState
()
{
void
initState
()
{
super
.
initState
();
super
.
initState
();
_incluirSubcarpetas
=
false
;
_incluirSubcarpetas
=
widget
.
_carpeta
.
incluyeSubcarpetas
;
for
(
TipoMultimedia
t
in
TipoMultimedia
.
values
){
for
(
TipoMultimedia
t
in
TipoMultimedia
.
values
){
_formatos
[
t
]
=
[];
_formatos
[
t
]
=
[];
...
@@ -83,6 +94,8 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
...
@@ -83,6 +94,8 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
onChanged:
(
bool
?
value
)
{
onChanged:
(
bool
?
value
)
{
setState
(()
{
setState
(()
{
_incluirSubcarpetas
=
value
!;
_incluirSubcarpetas
=
value
!;
widget
.
_carpeta
.
pressIncluirSubcarpetas
();
widget
.
_lista
.
actualizaSeleccionable
(
widget
.
_indice
,
widget
.
_carpeta
);
});
});
})
})
],
],
...
@@ -136,8 +149,10 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
...
@@ -136,8 +149,10 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
for
(
InfoFormato
i
in
widget
.
_formatosCarpeta
){
for
(
InfoFormato
i
in
widget
.
_formatosCarpeta
){
if
(
_formatos
[
t
]!.
contains
(
i
.
formatoOriginal
)
&&
!(!
_incluirSubcarpetas
&&
i
.
subcarpeta
)){
if
(
_formatos
[
t
]!.
contains
(
i
.
formatoOriginal
)
&&
!(!
_incluirSubcarpetas
&&
i
.
subcarpeta
)){
_seleccionados
[
i
.
formatoOriginal
]
=
_allOfType
[
t
]!;
_seleccionados
[
i
.
formatoOriginal
]
=
_allOfType
[
t
]!;
widget
.
_carpeta
.
pressAltSeleccionado
(
widget
.
_carpeta
.
formatos
.
indexOf
(
i
));
}
}
}
}
widget
.
_lista
.
actualizaSeleccionable
(
widget
.
_indice
,
widget
.
_carpeta
);
});
});
})
})
],
],
...
@@ -186,6 +201,8 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
...
@@ -186,6 +201,8 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
_seleccionados
[
i
.
formatoOriginal
]
=
value
!;
_seleccionados
[
i
.
formatoOriginal
]
=
value
!;
_allOfType
[
i
.
formatoOriginal
.
tipoMultimedia
]
=
_allOfType
[
i
.
formatoOriginal
.
tipoMultimedia
]
=
_actualizarCheckboxTipo
(
i
.
formatoOriginal
.
tipoMultimedia
);
_actualizarCheckboxTipo
(
i
.
formatoOriginal
.
tipoMultimedia
);
widget
.
_carpeta
.
pressAltSeleccionado
(
widget
.
_carpeta
.
formatos
.
indexOf
(
i
));
widget
.
_lista
.
actualizaSeleccionable
(
widget
.
_indice
,
widget
.
_carpeta
);
});
});
}),
}),
IconButton
(
IconButton
(
...
@@ -194,7 +211,12 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
...
@@ -194,7 +211,12 @@ class _PaginaConfiguracionCarpetaState extends State<PaginaConfiguracionCarpeta>
()
{
()
{
Navigator
.
push
(
context
,
Navigator
.
push
(
context
,
MaterialPageRoute
(
builder:
(
context
)
{
MaterialPageRoute
(
builder:
(
context
)
{
return
PaginaConfiguracion
(
elementoAsociado:
i
.
conversion
);
return
PaginaConfiguracion
(
indice:
widget
.
_indice
,
elemento:
i
.
conversion
,
lista:
widget
.
_lista
,
carpeta:
widget
.
_carpeta
);
}
}
));
));
},
},
...
...
lib/paginas/pagina_conversion.dart
View file @
54232159
...
@@ -2,12 +2,39 @@ import 'package:flutter/material.dart';
...
@@ -2,12 +2,39 @@ import 'package:flutter/material.dart';
import
'package:prueba_multimedia/modelo/modelo.dart'
;
import
'package:prueba_multimedia/modelo/modelo.dart'
;
class
PaginaConversion
extends
StatefulWidget
{
class
PaginaConversion
extends
StatefulWidget
{
final
ListaSeleccionables
_lista
;
final
int
_indiceArchivo
;
final
Carpeta
?
_carpeta
;
final
InfoFormato
?
_infoFormato
;
final
Convertible
?
_archivo
;
final
Formato
_formatoOriginal
;
final
Formato
_formatoOriginal
;
const
PaginaConversion
({
const
PaginaConversion
.
convertible
({
super
.
key
,
super
.
key
,
required
formatoOriginal
required
Formato
formatoOriginal
,
}):
_formatoOriginal
=
formatoOriginal
;
required
int
indiceArchivo
,
required
Convertible
elemento
,
required
ListaSeleccionables
lista
}):
_formatoOriginal
=
formatoOriginal
,
_indiceArchivo
=
indiceArchivo
,
_archivo
=
elemento
,
_carpeta
=
null
,
_infoFormato
=
null
,
_lista
=
lista
;
const
PaginaConversion
.
carpeta
({
super
.
key
,
required
Formato
formatoOriginal
,
required
int
indiceArchivo
,
required
Carpeta
carpeta
,
required
InfoFormato
infoFormato
,
required
ListaSeleccionables
lista
}):
_formatoOriginal
=
formatoOriginal
,
_indiceArchivo
=
indiceArchivo
,
_archivo
=
null
,
_carpeta
=
carpeta
,
_infoFormato
=
infoFormato
,
_lista
=
lista
;
@override
@override
State
<
PaginaConversion
>
createState
()
=>
_PaginaConversionState
();
State
<
PaginaConversion
>
createState
()
=>
_PaginaConversionState
();
...
@@ -15,10 +42,8 @@ class PaginaConversion extends StatefulWidget {
...
@@ -15,10 +42,8 @@ class PaginaConversion extends StatefulWidget {
class
_PaginaConversionState
extends
State
<
PaginaConversion
>
class
_PaginaConversionState
extends
State
<
PaginaConversion
>
with
SingleTickerProviderStateMixin
{
with
SingleTickerProviderStateMixin
{
// Podríamos hacer que en vez de poder haber nulos sea el mismo formato
// que el de origen de manera predeterminada ?
Formato
?
_formatoConvertido
;
Formato
?
_formatoConvertido
;
Calidad
calidadActual
=
Calidad
.
media
;
Calidad
?
_calidadActual
=
null
;
bool
_showProfiles
=
true
;
bool
_showProfiles
=
true
;
late
final
TabController
_tabController
;
late
final
TabController
_tabController
;
...
@@ -27,6 +52,12 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -27,6 +52,12 @@ class _PaginaConversionState extends State<PaginaConversion>
void
initState
()
{
void
initState
()
{
super
.
initState
();
super
.
initState
();
_tabController
=
TabController
(
length:
3
,
vsync:
this
);
_tabController
=
TabController
(
length:
3
,
vsync:
this
);
if
(
widget
.
_carpeta
!=
null
){
_formatoConvertido
=
widget
.
_infoFormato
!.
formatoDestino
;
}
else
{
_formatoConvertido
=
widget
.
_archivo
!.
formatoDestino
;
}
}
}
@override
@override
...
@@ -43,11 +74,11 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -43,11 +74,11 @@ class _PaginaConversionState extends State<PaginaConversion>
Row
(
Row
(
mainAxisAlignment:
MainAxisAlignment
.
center
,
mainAxisAlignment:
MainAxisAlignment
.
center
,
children:
[
children:
[
_create
OriginalFormatBox
(
),
_create
FormatBox
(
true
),
const
SizedBox
(
width:
10.0
),
const
SizedBox
(
width:
10.0
),
Icon
(
Icons
.
chevron_right
),
Icon
(
Icons
.
chevron_right
),
const
SizedBox
(
width:
10.0
),
const
SizedBox
(
width:
10.0
),
_create
ConversionFormatBox
(
)
_create
FormatBox
(
false
)
],
],
),
),
SizedBox
(
height:
20.0
),
SizedBox
(
height:
20.0
),
...
@@ -60,34 +91,21 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -60,34 +91,21 @@ class _PaginaConversionState extends State<PaginaConversion>
);
);
}
}
Widget
_createOriginalFormatBox
(){
Widget
_createFormatBox
(
bool
original
){
final
String
nombreFormato
=
widget
.
_formatoOriginal
.
name
.
toUpperCase
();
return
DecoratedBox
(
decoration:
BoxDecoration
(
border:
Border
.
all
(
color:
Colors
.
black
,
),
borderRadius:
BorderRadius
.
circular
(
15
),
color:
Colors
.
black26
),
child:
Padding
(
padding:
const
EdgeInsets
.
all
(
13.0
),
child:
Text
(
nombreFormato
,
style:
Theme
.
of
(
context
).
textTheme
.
titleLarge
,
textScaler:
TextScaler
.
linear
(
1.3
)
),
)
);
}
_createConversionFormatBox
()
{
final
String
nombreFormato
;
final
String
nombreFormato
;
if
(
_formatoConvertido
==
null
){
final
Color
fondo
;
nombreFormato
=
' '
;
if
(
original
){
}
else
{
nombreFormato
=
widget
.
_formatoOriginal
.
name
.
toUpperCase
();
nombreFormato
=
_formatoConvertido
!.
name
.
toUpperCase
();
fondo
=
Colors
.
black26
;
}
else
{
if
(
_formatoConvertido
==
null
){
nombreFormato
=
' '
;
fondo
=
Colors
.
white
;
}
else
{
nombreFormato
=
_formatoConvertido
!.
name
.
toUpperCase
();
fondo
=
Theme
.
of
(
context
).
colorScheme
.
inversePrimary
;
}
}
}
return
DecoratedBox
(
return
DecoratedBox
(
...
@@ -96,7 +114,7 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -96,7 +114,7 @@ class _PaginaConversionState extends State<PaginaConversion>
color:
Colors
.
black
,
color:
Colors
.
black
,
),
),
borderRadius:
BorderRadius
.
circular
(
15
),
borderRadius:
BorderRadius
.
circular
(
15
),
color:
_formatoConvertido
==
null
?
Colors
.
white
:
Colors
.
black12
color:
fondo
),
),
child:
Padding
(
child:
Padding
(
padding:
const
EdgeInsets
.
all
(
13.0
),
padding:
const
EdgeInsets
.
all
(
13.0
),
...
@@ -109,22 +127,16 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -109,22 +127,16 @@ class _PaginaConversionState extends State<PaginaConversion>
);
);
}
}
// TODO: A QUÉ SE REFIERE LA CALIDAD ?
/*
Un formato puede tener una calidad predeterminada?
De que sirve cambiar la calidad de un formato?
Hay formatos lossless para los que no hay ajustes de calidad/compresión
*/
// TODO: IMPLEMENTAR SISTEMA CALIDAD FORMATOS
/// Comportamiento temporal: Mostrar todas las calidades
/// Comportamiento temporal: Mostrar todas las calidades
Widget
_createCalidadSelectionPanel
()
{
Widget
_createCalidadSelectionPanel
()
{
final
listaChips
=
Calidad
.
values
.
map
((
elemento
)
{
final
listaChips
=
Calidad
.
values
.
map
((
elemento
)
{
return
ChoiceChip
(
return
ChoiceChip
(
selected:
elemento
==
calidadActual
,
selected:
elemento
==
_
calidadActual
,
shape:
StadiumBorder
(),
shape:
StadiumBorder
(),
label:
Text
(
elemento
.
texto
),
label:
Text
(
elemento
.
texto
),
// TODO: CAMBIAR CALIDAD FORMATO
// TODO: CAMBIAR CALIDAD FORMATO
onSelected:
(
selected
)
{
setState
((){
calidadActual
=
elemento
;});
},
onSelected:
(
_formatoConvertido
==
null
)?
null
:
(
selected
)
{
setState
((){
_calidadActual
=
elemento
;});
},
);
);
}).
toList
();
}).
toList
();
...
@@ -153,18 +165,37 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -153,18 +165,37 @@ class _PaginaConversionState extends State<PaginaConversion>
}
}
}
}
Widget
_createDefaultConversionPanel
()
{
Widget
_createTabVideos
(){
final
tabs
=
<
Widget
>[];
final
grids
=
<
Widget
>[];
final
tipos
=
TipoMultimedia
.
values
;
for
(
var
element
in
tipos
)
{
if
(
widget
.
_carpeta
!=
null
&&
element
==
TipoMultimedia
.
imagen
)
continue
;
tabs
.
add
(
Tab
(
icon:
element
.
icono
,
text:
element
.
nombre
,
));
grids
.
add
(
GridView
.
count
(
crossAxisCount:
3
,
crossAxisSpacing:
12
,
mainAxisSpacing:
12
,
children:
_createGridBotonesConversion
(
tipo:
element
),
));
}
return
Material
(
return
Material
(
clipBehavior:
Clip
.
antiAlias
,
clipBehavior:
Clip
.
antiAlias
,
shape:
BeveledRectangleBorder
(
shape:
BeveledRectangleBorder
(
side:
BorderSide
(
side:
BorderSide
(
color:
Colors
.
black
,
color:
Colors
.
black
,
width:
1
width:
1
),
),
borderRadius:
BorderRadius
.
only
(
borderRadius:
BorderRadius
.
only
(
topLeft:
Radius
.
circular
(
20.0
),
topLeft:
Radius
.
circular
(
20.0
),
topRight:
Radius
.
circular
(
20.0
)
topRight:
Radius
.
circular
(
20.0
)
)
)
),
),
child:
Container
(
child:
Container
(
height:
MediaQuery
.
of
(
context
).
size
.
height
-
380
,
height:
MediaQuery
.
of
(
context
).
size
.
height
-
380
,
...
@@ -176,15 +207,19 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -176,15 +207,19 @@ class _PaginaConversionState extends State<PaginaConversion>
children:
[
children:
[
_createBotonesPerfilFormato
(),
_createBotonesPerfilFormato
(),
SizedBox
(
SizedBox
(
height:
MediaQuery
.
of
(
context
).
size
.
height
-
460
,
height:
68
,
child:
TabBar
(
controller:
_tabController
,
tabs:
tabs
),
),
SizedBox
(
height:
MediaQuery
.
of
(
context
).
size
.
height
-
528
,
child:
Padding
(
child:
Padding
(
padding:
const
EdgeInsets
.
only
(
top:
16.0
),
padding:
const
EdgeInsets
.
only
(
top:
16.0
),
child:
GridView
.
count
(
child:
TabBarView
(
crossAxisCount:
_showProfiles
?
1
:
3
,
controller:
_tabController
,
childAspectRatio:
_showProfiles
?
6.0
:
1.0
,
children:
grids
crossAxisSpacing:
12
,
mainAxisSpacing:
12
,
children:
_showProfiles
?
_createListPerfiles
()
:
_createGridBotonesConversion
()
),
),
),
),
),
),
...
@@ -195,18 +230,18 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -195,18 +230,18 @@ class _PaginaConversionState extends State<PaginaConversion>
);
);
}
}
Widget
_create
TabVideos
()
{
Widget
_create
DefaultConversionPanel
()
{
return
Material
(
return
Material
(
clipBehavior:
Clip
.
antiAlias
,
clipBehavior:
Clip
.
antiAlias
,
shape:
BeveledRectangleBorder
(
shape:
BeveledRectangleBorder
(
side:
BorderSide
(
side:
BorderSide
(
color:
Colors
.
black
,
color:
Colors
.
black
,
width:
1
width:
1
),
),
borderRadius:
BorderRadius
.
only
(
borderRadius:
BorderRadius
.
only
(
topLeft:
Radius
.
circular
(
20.0
),
topLeft:
Radius
.
circular
(
20.0
),
topRight:
Radius
.
circular
(
20.0
)
topRight:
Radius
.
circular
(
20.0
)
)
)
),
),
child:
Container
(
child:
Container
(
height:
MediaQuery
.
of
(
context
).
size
.
height
-
380
,
height:
MediaQuery
.
of
(
context
).
size
.
height
-
380
,
...
@@ -218,39 +253,15 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -218,39 +253,15 @@ class _PaginaConversionState extends State<PaginaConversion>
children:
[
children:
[
_createBotonesPerfilFormato
(),
_createBotonesPerfilFormato
(),
SizedBox
(
SizedBox
(
height:
68
,
height:
MediaQuery
.
of
(
context
).
size
.
height
-
460
,
child:
TabBar
(
controller:
_tabController
,
tabs:
<
Widget
>[
Tab
(
icon:
TipoMultimedia
.
video
.
icono
,
text:
'Vídeo'
,
),
Tab
(
icon:
TipoMultimedia
.
audio
.
icono
,
text:
'Audio'
,
),
Tab
(
icon:
TipoMultimedia
.
imagen
.
icono
,
text:
'Imagen'
,
)
]
),
),
SizedBox
(
height:
MediaQuery
.
of
(
context
).
size
.
height
-
528
,
child:
Padding
(
child:
Padding
(
padding:
const
EdgeInsets
.
only
(
top:
16.0
),
padding:
const
EdgeInsets
.
only
(
top:
16.0
),
child:
TabBarView
(
child:
GridView
.
count
(
controller:
_tabController
,
crossAxisCount:
_showProfiles
?
1
:
3
,
children:
TipoMultimedia
.
values
.
map
((
tipo
)
{
childAspectRatio:
_showProfiles
?
6.0
:
1.0
,
return
GridView
.
count
(
crossAxisSpacing:
12
,
crossAxisCount:
3
,
mainAxisSpacing:
12
,
crossAxisSpacing:
12
,
children:
_showProfiles
?
_createListPerfiles
()
:
_createGridBotonesConversion
()
mainAxisSpacing:
12
,
children:
_createGridBotonesConversion
(
tipo:
tipo
)
);
}).
toList
()
),
),
),
),
),
),
...
@@ -269,7 +280,7 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -269,7 +280,7 @@ class _PaginaConversionState extends State<PaginaConversion>
shape:
RoundedRectangleBorder
(
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
20.0
),
borderRadius:
BorderRadius
.
circular
(
20.0
),
),
),
color:
(
_showProfiles
)?
Theme
.
of
(
context
).
disabledColor
:
Theme
.
of
(
context
).
cardColor
,
color:
(
_showProfiles
)?
Theme
.
of
(
context
).
colorScheme
.
inversePrimary
:
Theme
.
of
(
context
).
cardColor
,
child:
InkWell
(
child:
InkWell
(
onTap:
()
{
onTap:
()
{
setState
(()
{
setState
(()
{
...
@@ -290,7 +301,7 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -290,7 +301,7 @@ class _PaginaConversionState extends State<PaginaConversion>
shape:
RoundedRectangleBorder
(
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
20.0
),
borderRadius:
BorderRadius
.
circular
(
20.0
),
),
),
color:
(!
_showProfiles
)?
Theme
.
of
(
context
).
disabledColor
:
Theme
.
of
(
context
).
cardColor
,
color:
(!
_showProfiles
)?
Theme
.
of
(
context
).
colorScheme
.
inversePrimary
:
Theme
.
of
(
context
).
cardColor
,
child:
InkWell
(
child:
InkWell
(
onTap:
()
{
onTap:
()
{
setState
(()
{
setState
(()
{
...
@@ -310,7 +321,6 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -310,7 +321,6 @@ class _PaginaConversionState extends State<PaginaConversion>
);
);
}
}
// TODO: HABLAR SOBRE CÓMO HACER LOS PERFILES
List
<
Widget
>
_createListPerfiles
(){
List
<
Widget
>
_createListPerfiles
(){
final
toRet
=
<
Widget
>[];
final
toRet
=
<
Widget
>[];
...
@@ -323,43 +333,30 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -323,43 +333,30 @@ class _PaginaConversionState extends State<PaginaConversion>
if
(
widget
.
_formatoOriginal
.
tipoMultimedia
==
TipoMultimedia
.
audio
){
if
(
widget
.
_formatoOriginal
.
tipoMultimedia
==
TipoMultimedia
.
audio
){
formatoPerfil
=
perfil
.
extensionMusica
;
formatoPerfil
=
perfil
.
extensionMusica
;
}
}
//
if
(
formatoPerfil
!=
null
&&
formatoPerfil
!=
widget
.
_formatoOriginal
){
if
(
formatoPerfil
!=
null
){
/**
Color
color
=
Theme
.
of
(
context
).
cardColor
;
* Entiendo que si el archivo ya se encuentra en un formato que
if
(
formatoPerfil
==
widget
.
_formatoOriginal
){
* es el mismo que se usa para un cierto perfil entonces ese perfil
color
=
Theme
.
of
(
context
).
disabledColor
;
* esté desabilitado, pero podría llegar a ser confuso ya que no
}
* se especifica por ningún sitio al usuario el por qué esa opción
if
(
formatoPerfil
==
_formatoConvertido
&&
perfil
.
calidad
==
_calidadActual
){
* no está disponible.
color
=
Theme
.
of
(
context
).
colorScheme
.
inversePrimary
;
*
}
* Además, no se como compaginar esto con que cada formato pueda
* tener un nivel de calidad diferente, porque podríamos tener
* hipotéticamente un formato como jpg (que es de baja calidad) pero con
* un valor de calidad alto
*
* En aplicaciones como gimp por ejemplo se puede especificar el nivel
* de compresión (inverso a la calidad) de formatos como jpg
bool desabilitado = (_formatoConvertido == formatoPerfil) &&
(_formatoConvertido?.calidad == perfil.calidad);
**/
toRet
.
add
(
Material
(
toRet
.
add
(
Material
(
shape:
RoundedRectangleBorder
(
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
20.0
),
borderRadius:
BorderRadius
.
circular
(
20.0
),
),
),
// TODO: ANALIZAR SI DESABILITAR PERFILES O NO
color:
color
,
// color: desabilitado ? Theme.of(context).disabledColor : Theme.of(context).cardColor,
color:
Theme
.
of
(
context
).
cardColor
,
child:
InkWell
(
child:
InkWell
(
onTap:
()
{
onTap:
(
formatoPerfil
==
widget
.
_formatoOriginal
)?
()
{
if
(
_formatoConvertido
!=
formatoPerfil
)
{
ScaffoldMessenger
.
of
(
context
).
showSnackBar
(
setState
(()
{
SnackBar
(
// TODO: IMPLEMENTAR SISTEMA CALIDAD FORMATOS
content:
Text
(
'El archivo ya coincide con este perfil'
),
// _formatoConvertido = Formato(formato: formatoPerfil!, calidad: perfil.calidad);
),
_formatoConvertido
=
formatoPerfil
;
);
});
}
:
()
{
if
(
_formatoConvertido
!=
formatoPerfil
&&
_calidadActual
!=
perfil
.
calidad
)
{
_cambiarFormatoCalidad
(
formatoPerfil
!,
perfil
.
calidad
);
}
}
},
},
child:
Container
(
child:
Container
(
...
@@ -396,16 +393,16 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -396,16 +393,16 @@ class _PaginaConversionState extends State<PaginaConversion>
shape:
RoundedRectangleBorder
(
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
20.0
),
borderRadius:
BorderRadius
.
circular
(
20.0
),
),
),
color:
_formatoConvertido
==
elemento
?
Theme
.
of
(
context
).
disabledColor
color:
_formatoConvertido
==
elemento
?
Theme
.
of
(
context
).
colorScheme
.
inversePrimary
:
Theme
.
of
(
context
).
cardColor
,
:
Theme
.
of
(
context
).
cardColor
,
child:
InkWell
(
child:
InkWell
(
/*
borderRadius:
BorderRadius
.
circular
(
20.0
),
TODO: COMPORTAMIENTO DE LOS BOTONES
onTap:
_formatoConvertido
==
elemento
?
()
{
onTap:
_formatoConvertido
==
elemento
?
()
{
setState(() { _formatoConvertido = null; });
setState
(()
{
} :
_formatoConvertido
=
_calidadActual
=
null
;
*/
_cambiarFormatoCalidad
(
null
,
null
);
onTap:
()
{
setState
((){
_formatoConvertido
=
elemento
;});
},
});
}
:
()
=>
_cambiarFormatoCalidad
(
elemento
,
Calidad
.
media
),
onLongPress:
()
{
onLongPress:
()
{
showDialog
<
void
>(
showDialog
<
void
>(
context:
context
,
context:
context
,
...
@@ -450,4 +447,25 @@ class _PaginaConversionState extends State<PaginaConversion>
...
@@ -450,4 +447,25 @@ class _PaginaConversionState extends State<PaginaConversion>
);
);
}).
toList
();
}).
toList
();
}
}
}
void
_cambiarFormatoCalidad
(
Formato
?
destino
,
Calidad
?
calidad
){
setState
((){
_formatoConvertido
=
destino
;
_calidadActual
=
calidad
;
ElementoSeleccionable
resultado
;
if
(
widget
.
_carpeta
!=
null
){
widget
.
_carpeta
!.
setFormatoDestino
(
widget
.
_formatoOriginal
,
_formatoConvertido
);
resultado
=
widget
.
_carpeta
!;
}
else
{
widget
.
_archivo
!.
formatoDestino
=
_formatoConvertido
;
resultado
=
widget
.
_archivo
!;
}
// TODO: ACTUALIZAR CALIDAD
widget
.
_lista
.
actualizaSeleccionable
(
widget
.
_indiceArchivo
,
resultado
);
});
}
}
\ No newline at end of file
lib/paginas/pagina_principal_llena.dart
View file @
54232159
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
import
'package:prueba_multimedia/modelo/modelo.dart'
;
import
'package:prueba_multimedia/modelo/modelo.dart'
;
import
'package:prueba_multimedia/widgets/carpeta_widget.dart'
;
import
'package:prueba_multimedia/widgets/widgets.dart'
;
import
'package:prueba_multimedia/widgets/widgets.dart'
;
class
PaginaPrincipalLlena
extends
StatelessWidget
{
class
PaginaPrincipalLlena
extends
StatelessWidget
{
...
@@ -19,7 +20,48 @@ class PaginaPrincipalLlena extends StatelessWidget {
...
@@ -19,7 +20,48 @@ class PaginaPrincipalLlena extends StatelessWidget {
return
const
SizedBox
(
height:
8.0
);
return
const
SizedBox
(
height:
8.0
);
},
},
itemBuilder:
(
context
,
index
)
{
itemBuilder:
(
context
,
index
)
{
return
SeleccionableWidget
(
seleccionable:
seleccionables
[
index
]);
return
Dismissible
(
key:
Key
(
seleccionables
[
index
].
id
),
background:
Container
(
color:
Colors
.
red
,
alignment:
Alignment
.
centerLeft
,
child:
Padding
(
padding:
const
EdgeInsets
.
all
(
4.0
),
child:
Icon
(
Icons
.
delete
,
color:
Colors
.
white
,
size:
31.0
),
),
),
secondaryBackground:
Container
(
color:
Colors
.
red
,
alignment:
Alignment
.
centerRight
,
child:
Padding
(
padding:
const
EdgeInsets
.
all
(
4.0
),
child:
Icon
(
Icons
.
delete
,
color:
Colors
.
white
,
size:
31.0
),
),
),
onDismissed:
(
direction
)
{
listaSeleccionables
.
borraSeleccionable
(
index
);
ScaffoldMessenger
.
of
(
context
).
showSnackBar
(
SnackBar
(
content:
Text
(
'
${seleccionables[index].nombre}
borrado'
),
action:
SnackBarAction
(
label:
'Deshacer'
,
onPressed:
()
{
listaSeleccionables
.
reinsertar
(
index
,
seleccionables
[
index
]);
}
),
)
);
},
child:
(
seleccionables
[
index
]
is
Carpeta
)?
CarpetaWidget
(
indice:
index
,
carpeta:
seleccionables
[
index
]
as
Carpeta
,
lista:
listaSeleccionables
)
:
SeleccionableWidget
(
indice:
index
,
seleccionable:
seleccionables
[
index
],
lista:
listaSeleccionables
)
);
},
},
),
),
);
);
...
...
lib/widgets/carpeta_widget.dart
0 → 100644
View file @
54232159
import
'package:flutter/material.dart'
;
import
'package:prueba_multimedia/paginas/paginas.dart'
;
import
'package:prueba_multimedia/modelo/modelo.dart'
;
import
'dart:math'
;
class
CarpetaWidget
extends
StatefulWidget
{
final
int
indice
;
final
Carpeta
carpeta
;
final
ListaSeleccionables
lista
;
const
CarpetaWidget
({
super
.
key
,
required
this
.
indice
,
required
this
.
carpeta
,
required
this
.
lista
});
@override
State
<
CarpetaWidget
>
createState
()
=>
_CarpetaWidgetState
();
}
class
_CarpetaWidgetState
extends
State
<
CarpetaWidget
>
with
SingleTickerProviderStateMixin
{
static
double
MAX_HEIGHT
=
50
;
late
final
AnimationController
_controller
;
List
<
InfoFormato
>
seleccionados
=
[];
bool
open
=
false
;
double
rotAngle
=
0
;
double
height
=
0
;
@override
void
initState
()
{
_controller
=
AnimationController
(
duration:
Duration
(
milliseconds:
200
),
vsync:
this
);
_controller
.
addListener
(()
{
setState
(()
{
rotAngle
=
pi
*
_controller
.
value
;
height
=
MAX_HEIGHT
*
_controller
.
value
;
});
});
super
.
initState
();
}
@override
Widget
build
(
BuildContext
context
)
{
seleccionados
=
[];
for
(
var
i
in
widget
.
carpeta
.
formatos
){
if
(
i
.
seleccionado
&&
(
widget
.
carpeta
.
incluyeSubcarpetas
||
!
i
.
subcarpeta
)){
seleccionados
.
add
(
i
);
}
}
if
(
seleccionados
.
length
<=
0
){
_controller
.
reset
();
}
return
SizedBox
(
height:
(
height
<=
0
)?
60
:
60
+
(
seleccionados
.
length
*(
height
+
10
)),
width:
MediaQuery
.
of
(
context
).
size
.
width
,
child:
Stack
(
children:
[
Positioned
(
top:
0
,
child:
buildMainContainer
(),
),
...
buildSecondaryContainers
()
]
),
);
}
Widget
buildMainContainer
(){
String
s
=
""
;
if
(
seleccionados
.
length
>
1
)
s
=
"s"
;
return
SizedBox
(
height:
60
,
width:
MediaQuery
.
of
(
context
).
size
.
width
-
10
,
child:
Row
(
crossAxisAlignment:
CrossAxisAlignment
.
center
,
children:
<
Widget
>[
Flexible
(
flex:
1
,
child:
widget
.
carpeta
.
icono
),
Flexible
(
flex:
1
,
child:
const
SizedBox
(
width:
20
)),
Flexible
(
flex:
15
,
child:
SizedBox
.
expand
(
child:
Column
(
crossAxisAlignment:
CrossAxisAlignment
.
start
,
mainAxisAlignment:
MainAxisAlignment
.
center
,
children:
[
Flexible
(
flex:
1
,
child:
Text
(
widget
.
carpeta
.
nombre
,
style:
Theme
.
of
(
context
).
textTheme
.
bodyLarge
?.
copyWith
(
fontWeight:
FontWeight
.
bold
),
overflow:
TextOverflow
.
ellipsis
,
),
),
Flexible
(
flex:
1
,
child:
Text
(
(
seleccionados
.
length
>
0
)?
'
${seleccionados.length}
formato
$s
seleccionado
$s
'
:
'Ningún formato seleccionado'
,
style:
Theme
.
of
(
context
).
textTheme
.
bodyLarge
?.
copyWith
(
color:
(
seleccionados
.
length
>
0
)?
null
:
Colors
.
red
)
),
),
],
)
),
),
Flexible
(
flex:
3
,
fit:
FlexFit
.
loose
,
child:
Transform
.
rotate
(
angle:
rotAngle
,
child:
IconButton
(
icon:
Icon
(
Icons
.
arrow_drop_down
,
color:
(
seleccionados
.
length
>
0
)?
null
:
Theme
.
of
(
context
).
disabledColor
,
),
onPressed:
(
seleccionados
.
length
<=
0
)?
null
:
()
{
setState
(()
{
open
=
!
open
;
});
widget
.
carpeta
.
pressOpenClose
();
_controller
.
toggle
();
widget
.
lista
.
actualizaSeleccionable
(
widget
.
indice
,
widget
.
carpeta
);
}
),
),
),
Flexible
(
flex:
3
,
child:
IconButton
(
icon:
const
Icon
(
Icons
.
edit
),
onPressed:
()
{
Navigator
.
push
(
context
,
MaterialPageRoute
(
builder:
(
context
)
{
return
PaginaConfiguracion
(
indice:
widget
.
indice
,
elemento:
widget
.
carpeta
,
lista:
widget
.
lista
);
}));
},
),
)
]
),
);
}
List
<
Widget
>
buildSecondaryContainers
(){
int
index
=
0
;
return
seleccionados
.
map
((
elemento
)
{
index
++;
String
texto
=
elemento
.
formatoOriginal
.
name
.
toUpperCase
();
if
(
elemento
.
formatoDestino
!=
null
)
texto
+=
" >
${elemento.formatoDestino!.name.toUpperCase()}
"
;
return
Positioned
(
top:
(
height
+
10
)*
index
,
child:
ClipRect
(
clipper:
_MyRectClipper
(
_controller
),
child:
Dismissible
(
key:
Key
(
elemento
.
conversion
.
id
),
background:
Container
(
color:
Colors
.
red
,
alignment:
Alignment
.
centerLeft
,
child:
Padding
(
padding:
const
EdgeInsets
.
only
(
left:
4.0
),
child:
Icon
(
Icons
.
check_box_outline_blank
,
color:
Colors
.
white
,
size:
31.0
),
),
),
secondaryBackground:
Container
(
color:
Colors
.
red
,
alignment:
Alignment
.
centerRight
,
child:
Padding
(
padding:
const
EdgeInsets
.
only
(
right:
14.0
),
child:
Icon
(
Icons
.
check_box_outline_blank
,
color:
Colors
.
white
,
size:
31.0
),
),
),
onDismissed:
(
direction
)
{
seleccionados
.
remove
(
elemento
);
widget
.
carpeta
.
pressAltSeleccionado
(
widget
.
carpeta
.
formatos
.
indexOf
(
elemento
));
widget
.
lista
.
actualizaSeleccionable
(
widget
.
indice
,
widget
.
carpeta
);
ScaffoldMessenger
.
of
(
context
).
showSnackBar
(
SnackBar
(
content:
Text
(
'
${elemento.formatoOriginal.name.toUpperCase()}
excluido de
${widget.carpeta.nombre}
'
),
action:
SnackBarAction
(
label:
'Deshacer'
,
onPressed:
()
{
seleccionados
.
add
(
elemento
);
widget
.
carpeta
.
pressAltSeleccionado
(
widget
.
carpeta
.
formatos
.
indexOf
(
elemento
));
widget
.
lista
.
actualizaSeleccionable
(
widget
.
indice
,
widget
.
carpeta
);
}
),
)
);
},
child:
SizedBox
(
height:
50
,
width:
MediaQuery
.
of
(
context
).
size
.
width
-
10
,
child:
Padding
(
padding:
const
EdgeInsets
.
only
(
left:
24.0
),
child:
Row
(
crossAxisAlignment:
CrossAxisAlignment
.
center
,
children:
<
Widget
>[
Flexible
(
flex:
1
,
child:
Icon
(
Icons
.
find_in_page_outlined
)),
Flexible
(
flex:
1
,
child:
const
SizedBox
(
width:
10
)),
Flexible
(
flex:
13
,
child:
SizedBox
.
expand
(
child:
Column
(
crossAxisAlignment:
CrossAxisAlignment
.
start
,
mainAxisAlignment:
MainAxisAlignment
.
center
,
children:
[
Flexible
(
flex:
1
,
child:
Text
(
widget
.
carpeta
.
nombre
,
style:
Theme
.
of
(
context
).
textTheme
.
bodyLarge
?.
copyWith
(
fontWeight:
FontWeight
.
bold
),
overflow:
TextOverflow
.
ellipsis
),
),
Flexible
(
flex:
1
,
child:
Text
(
texto
,
style:
Theme
.
of
(
context
).
textTheme
.
bodyLarge
?.
copyWith
(
fontWeight:
FontWeight
.
bold
)
),
),
],
)
),
),
Flexible
(
flex:
2
,
child:
IconButton
(
icon:
const
Icon
(
Icons
.
edit
),
onPressed:
()
{
Navigator
.
push
(
context
,
MaterialPageRoute
(
builder:
(
context
)
{
return
PaginaConfiguracion
(
indice:
widget
.
indice
,
elemento:
elemento
.
conversion
,
lista:
widget
.
lista
,
carpeta:
widget
.
carpeta
);
}
));
},
),
)
]
),
),
),
),
),
);
}).
toList
();
}
}
class
_MyRectClipper
extends
CustomClipper
<
Rect
>
{
final
AnimationController
_controller
;
_MyRectClipper
(
this
.
_controller
);
@override
Rect
getClip
(
Size
size
)
{
double
value
=
(
1
-
_controller
.
value
)*
_CarpetaWidgetState
.
MAX_HEIGHT
;
return
Rect
.
fromLTWH
(
0
,
value
,
1000
,
_CarpetaWidgetState
.
MAX_HEIGHT
);
}
@override
bool
shouldReclip
(
covariant
CustomClipper
<
Rect
>
oldClipper
)
{
return
!(
_controller
.
isDismissed
||
_controller
.
isCompleted
);
}
}
\ No newline at end of file
lib/widgets/seleccionable_widget.dart
View file @
54232159
...
@@ -3,40 +3,75 @@ import 'package:prueba_multimedia/paginas/paginas.dart';
...
@@ -3,40 +3,75 @@ import 'package:prueba_multimedia/paginas/paginas.dart';
import
'package:prueba_multimedia/modelo/modelo.dart'
;
import
'package:prueba_multimedia/modelo/modelo.dart'
;
class
SeleccionableWidget
extends
StatelessWidget
{
class
SeleccionableWidget
extends
StatelessWidget
{
final
int
indice
;
final
ElementoSeleccionable
seleccionable
;
final
ElementoSeleccionable
seleccionable
;
final
ListaSeleccionables
lista
;
const
SeleccionableWidget
({
super
.
key
,
required
this
.
seleccionable
});
const
SeleccionableWidget
({
super
.
key
,
required
this
.
indice
,
required
this
.
seleccionable
,
required
this
.
lista
});
// TODO: ACTUALIZAR PARA MOSTRAR FORMATOS Y CAMBIOS
// TODO: ACTUALIZAR PARA MOSTRAR FORMATOS Y CAMBIOS
@override
@override
Widget
build
(
BuildContext
context
)
{
Widget
build
(
BuildContext
context
)
{
return
Row
(
final
String
nombre
=
seleccionable
.
nombre
;
children:
<
Widget
>[
int
index
=
nombre
.
lastIndexOf
(
'.'
);
seleccionable
.
icono
,
final
String
visible
;
const
SizedBox
(
width:
10
,),
if
(
index
>
-
1
){
Expanded
(
visible
=
nombre
.
substring
(
0
,
index
);
child:
Column
(
}
crossAxisAlignment:
CrossAxisAlignment
.
start
,
else
{
children:
[
visible
=
nombre
;
Text
(
}
seleccionable
.
nombre
,
style:
Theme
.
of
(
context
).
textTheme
.
bodyLarge
),
Widget
?
formatoOrig
;
],
if
(
seleccionable
is
Convertible
){
Convertible
arch
=
(
seleccionable
as
Convertible
);
String
texto
=
arch
.
formatoOriginal
.
name
.
toUpperCase
();
if
(
arch
.
formatoDestino
!=
null
)
texto
+=
" >
${arch.formatoDestino!.name.toUpperCase()}
"
;
formatoOrig
=
Flexible
(
flex:
1
,
child:
Text
(
texto
));
}
return
SizedBox
(
height:
60
,
width:
MediaQuery
.
of
(
context
).
size
.
width
,
child:
Row
(
children:
<
Widget
>[
Flexible
(
flex:
1
,
child:
seleccionable
.
icono
),
Flexible
(
flex:
1
,
child:
const
SizedBox
(
width:
15
)),
Flexible
(
flex:
16
,
child:
SizedBox
.
expand
(
child:
Column
(
crossAxisAlignment:
CrossAxisAlignment
.
start
,
children:
[
Flexible
(
flex:
1
,
child:
Text
(
visible
,
style:
Theme
.
of
(
context
).
textTheme
.
bodyLarge
?.
copyWith
(
fontWeight:
FontWeight
.
bold
)
),
),
if
(
formatoOrig
!=
null
)
formatoOrig
],
)
),
),
Flexible
(
flex:
2
,
child:
IconButton
(
icon:
const
Icon
(
Icons
.
edit
),
onPressed:
()
{
Navigator
.
push
(
context
,
MaterialPageRoute
(
builder:
(
context
)
{
return
PaginaConfiguracion
(
indice:
indice
,
elemento:
seleccionable
,
lista:
lista
);
}));
},
),
)
)
),
]
if
(
seleccionable
is
Carpeta
)
)
IconButton
(
onPressed:
()
{},
icon:
Icon
(
Icons
.
menu
)),
IconButton
(
icon:
const
Icon
(
Icons
.
edit
),
onPressed:
()
{
Navigator
.
push
(
context
,
MaterialPageRoute
(
builder:
(
context
)
{
return
PaginaConfiguracion
(
elementoAsociado:
seleccionable
);
}));
},
)
],
);
);
}
}
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment