11import React , { useEffect , useRef , useState } from 'react' ;
2- import { StyleSheet , View , Text , Animated } from 'react-native' ;
2+ import { StyleSheet , View , Text , Animated , Alert } from 'react-native' ;
33import { MessageBubbleProps , ToolWidget , TaskItem } from './types' ;
44import TaskListBubble from './TaskListBubble' ; // Nuovo componente card-based
55import TaskTableBubble from './TaskTableBubble' ; // Mantieni per backward compatibility
@@ -8,8 +8,10 @@ import WidgetBubble from './widgets/WidgetBubble';
88import VisualizationModal from './widgets/VisualizationModal' ;
99import ItemDetailModal from './widgets/ItemDetailModal' ;
1010import TaskEditModal from '../Task/TaskEditModal' ;
11+ import EditCategoryModal from '../Category/EditCategoryModal' ;
12+ import CategoryMenu from '../Category/CategoryMenu' ;
1113import { Task as TaskType } from '../../services/taskService' ;
12- import { updateTask } from '../../services/taskService' ;
14+ import { updateTask , updateCategory , deleteCategory } from '../../services/taskService' ;
1315
1416const MessageBubble : React . FC < MessageBubbleProps > = ( { message, style } ) => {
1517 const isBot = message . sender === 'bot' ;
@@ -31,6 +33,15 @@ const MessageBubble: React.FC<MessageBubbleProps> = ({ message, style }) => {
3133 const [ taskEditModalVisible , setTaskEditModalVisible ] = useState ( false ) ;
3234 const [ selectedTaskForEdit , setSelectedTaskForEdit ] = useState < TaskType | null > ( null ) ;
3335
36+ // Stato per category edit modal e menu
37+ const [ categoryEditModalVisible , setCategoryEditModalVisible ] = useState ( false ) ;
38+ const [ categoryMenuVisible , setCategoryMenuVisible ] = useState ( false ) ;
39+ const [ selectedCategoryForEdit , setSelectedCategoryForEdit ] = useState < any > ( null ) ;
40+ const [ editCategoryName , setEditCategoryName ] = useState ( '' ) ;
41+ const [ editCategoryDescription , setEditCategoryDescription ] = useState ( '' ) ;
42+ const [ isEditingCategory , setIsEditingCategory ] = useState ( false ) ;
43+ const [ isDeletingCategory , setIsDeletingCategory ] = useState ( false ) ;
44+
3445 // Animazioni per i punti di streaming
3546 const streamingDot1 = useRef ( new Animated . Value ( 0.5 ) ) . current ;
3647 const streamingDot2 = useRef ( new Animated . Value ( 0.5 ) ) . current ;
@@ -244,6 +255,100 @@ const MessageBubble: React.FC<MessageBubbleProps> = ({ message, style }) => {
244255 }
245256 } ;
246257
258+ // Handler per aprire il menu della categoria
259+ const handleCategoryPress = ( category : any ) => {
260+ console . log ( '[MessageBubble] handleCategoryPress called with:' , category ) ;
261+ setSelectedCategoryForEdit ( category ) ;
262+ setCategoryMenuVisible ( true ) ;
263+ } ;
264+
265+ // Handler per chiudere il menu della categoria
266+ const handleCloseCategoryMenu = ( ) => {
267+ setCategoryMenuVisible ( false ) ;
268+ } ;
269+
270+ // Handler per aprire la modal di modifica dalla voce menu
271+ const handleEditCategory = ( ) => {
272+ console . log ( '[MessageBubble] handleEditCategory - selectedCategoryForEdit:' , selectedCategoryForEdit ) ;
273+ console . log ( '[MessageBubble] handleEditCategory - name:' , selectedCategoryForEdit ?. name ) ;
274+ console . log ( '[MessageBubble] handleEditCategory - description:' , selectedCategoryForEdit ?. description ) ;
275+ setCategoryMenuVisible ( false ) ;
276+ setEditCategoryName ( selectedCategoryForEdit ?. name || '' ) ;
277+ setEditCategoryDescription ( selectedCategoryForEdit ?. description || '' ) ;
278+ setCategoryEditModalVisible ( true ) ;
279+ } ;
280+
281+ // Handler per salvare le modifiche alla categoria
282+ const handleSaveCategory = async ( ) => {
283+ if ( ! selectedCategoryForEdit ) return ;
284+
285+ if ( editCategoryName . trim ( ) === '' ) {
286+ Alert . alert ( 'Errore' , 'Il nome della categoria non può essere vuoto' ) ;
287+ return ;
288+ }
289+
290+ setIsEditingCategory ( true ) ;
291+ try {
292+ await updateCategory ( selectedCategoryForEdit . name , {
293+ name : editCategoryName . trim ( ) ,
294+ description : editCategoryDescription . trim ( )
295+ } ) ;
296+
297+ Alert . alert ( 'Successo' , 'Categoria aggiornata con successo' ) ;
298+ setCategoryEditModalVisible ( false ) ;
299+ setSelectedCategoryForEdit ( null ) ;
300+ } catch ( error ) {
301+ console . error ( '[MessageBubble] Error updating category:' , error ) ;
302+ Alert . alert ( 'Errore' , 'Impossibile aggiornare la categoria. Riprova più tardi.' ) ;
303+ } finally {
304+ setIsEditingCategory ( false ) ;
305+ }
306+ } ;
307+
308+ // Handler per chiudere la modal di modifica categoria
309+ const handleCancelCategoryEdit = ( ) => {
310+ setCategoryEditModalVisible ( false ) ;
311+ setEditCategoryName ( '' ) ;
312+ setEditCategoryDescription ( '' ) ;
313+ } ;
314+
315+ // Handler per eliminare una categoria
316+ const handleDeleteCategory = async ( ) => {
317+ if ( ! selectedCategoryForEdit ) return ;
318+
319+ Alert . alert (
320+ 'Conferma eliminazione' ,
321+ `Sei sicuro di voler eliminare la categoria "${ selectedCategoryForEdit . name } "?` ,
322+ [
323+ { text : 'Annulla' , style : 'cancel' } ,
324+ {
325+ text : 'Elimina' ,
326+ style : 'destructive' ,
327+ onPress : async ( ) => {
328+ setIsDeletingCategory ( true ) ;
329+ try {
330+ await deleteCategory ( selectedCategoryForEdit . name ) ;
331+ Alert . alert ( 'Successo' , 'Categoria eliminata con successo' ) ;
332+ setCategoryMenuVisible ( false ) ;
333+ setSelectedCategoryForEdit ( null ) ;
334+ } catch ( error ) {
335+ console . error ( '[MessageBubble] Error deleting category:' , error ) ;
336+ Alert . alert ( 'Errore' , 'Impossibile eliminare la categoria. Riprova più tardi.' ) ;
337+ } finally {
338+ setIsDeletingCategory ( false ) ;
339+ }
340+ } ,
341+ } ,
342+ ]
343+ ) ;
344+ } ;
345+
346+ // Handler placeholder per condivisione categoria
347+ const handleShareCategory = ( ) => {
348+ setCategoryMenuVisible ( false ) ;
349+ Alert . alert ( 'Info' , 'Funzionalità di condivisione non ancora disponibile nella chat' ) ;
350+ } ;
351+
247352 return (
248353 < Animated . View style = { [
249354 styles . messageContainer ,
@@ -264,6 +369,7 @@ const MessageBubble: React.FC<MessageBubbleProps> = ({ message, style }) => {
264369 onOpenVisualization = { handleOpenVisualization }
265370 onOpenItemDetail = { handleOpenItemDetail }
266371 onTaskPress = { handleTaskPress }
372+ onCategoryPress = { handleCategoryPress }
267373 />
268374 ) ) }
269375 </ View >
@@ -303,6 +409,7 @@ const MessageBubble: React.FC<MessageBubbleProps> = ({ message, style }) => {
303409 widget = { selectedVisualizationWidget }
304410 onClose = { ( ) => setVisualizationModalVisible ( false ) }
305411 onItemPress = { handleOpenItemDetail }
412+ onCategoryPress = { handleCategoryPress }
306413 />
307414 ) }
308415
@@ -326,6 +433,34 @@ const MessageBubble: React.FC<MessageBubbleProps> = ({ message, style }) => {
326433 onSave = { handleSaveTask }
327434 />
328435 ) }
436+
437+ { /* Category Menu */ }
438+ { selectedCategoryForEdit && (
439+ < CategoryMenu
440+ visible = { categoryMenuVisible }
441+ onClose = { handleCloseCategoryMenu }
442+ onEdit = { handleEditCategory }
443+ onDelete = { handleDeleteCategory }
444+ onShare = { handleShareCategory }
445+ isDeleting = { isDeletingCategory }
446+ isOwned = { selectedCategoryForEdit . isOwned !== undefined ? selectedCategoryForEdit . isOwned : true }
447+ permissionLevel = { selectedCategoryForEdit . permissionLevel || "READ_WRITE" }
448+ />
449+ ) }
450+
451+ { /* Category Edit Modal */ }
452+ { selectedCategoryForEdit && (
453+ < EditCategoryModal
454+ visible = { categoryEditModalVisible }
455+ onClose = { handleCancelCategoryEdit }
456+ onSave = { handleSaveCategory }
457+ title = { editCategoryName }
458+ description = { editCategoryDescription }
459+ onTitleChange = { setEditCategoryName }
460+ onDescriptionChange = { setEditCategoryDescription }
461+ isEditing = { isEditingCategory }
462+ />
463+ ) }
329464 </ Animated . View >
330465 ) ;
331466} ;
0 commit comments