5

Tengo un NSTextView básico con texto enriquecido y gráficos habilitados (en IB). Lo que me gustaría obtener es la ruta y el nombre de archivo de cualquier imagen arrastrada para poder pasarlos a otra clase.Obtener nombre de archivo y ruta desde nsfilewrapper/nstextattachment en NSAttributedString

Soy nuevo en NSAttributedString pero tengo un bucle usando enumerateAttributesInRange:options:usingBlock: buscando NSAttachmentAttributeName y todo funciona bien. Pero profundizando, llego a la clase fileWrapper y es apparent inability to give me the path of the item.

¿Cómo podría obtener el nombre y la ruta de acceso de NSTextAttachment?

Relacionado: ¿Hay alguna manera más fácil de obtenerlos todos y luego recorrer los atributos?

Gracias tanto!

+0

Desafortunadamente, el diccionario de atributos devuelto por NSFileWrapper tampoco proporciona la ruta completa. El diseño de NSFileWrapper hace suposiciones de encapsulación miopes y desafortunadas al no proporcionar acceso a la ruta de acceso del objeto de referencia original. – ctpenrose

Respuesta

8

Aunque yo personalmente mantienen el diseño de NSFileWrapper en desacato, si sólo tiene los datos de cada archivo adjunto que puede acceder a él como una instancia NSData a través del método de NSFileWrapper regularFileContents. Sin embargo, necesitaba una ruta de acceso válida y explícita para el archivo adjunto de mi aplicación. Obtenerlo es mucho más trabajo de lo que debería ser:

Puede subclasificar su NSTextView y anular el método NSDraggingDestination Protocol draggingEntered: y puede atravesar los objetos NSPasteboardItem pasados ​​a su aplicación durante la operación de arrastre. Elegí mantener el nombre de ruta y su número de inodo en un NSMutableDictionary, ya que NSFileWrapper puede proporcionarle el inode del archivo al que se hace referencia. Más tarde, cuando accedo al contenido de NSTextView a través de NSAttributedString, puedo buscar la ruta de acceso de un archivo adjunto usando el inode como índice.

- (NSDragOperation)draggingEntered:(id <NSDraggingInfo>)sender { 

    // get pasteboard from dragging operation 

    NSPasteboard *pasteboard = [sender draggingPasteboard]; 

    NSArray *pasteboardItems = [pasteboard pasteboardItems]; 

    for (NSPasteboardItem *pasteboardItem in pasteboardItems) { 

     // look for a file url type from the pasteboard item 

     NSString *draggedURLString = [pasteboardItem stringForType:@"public.file-url"]; 

     if (draggedURLString != nil) { 

      NSURL *draggedURL = [NSURL URLWithString:draggedURLString]; 

      NSString *draggedPath = [draggedURL path]; 

      NSLog(@"pathname: %@", draggedPath); 

      // do something with the path 

      // get file attributes 

      NSDictionary *draggedAttributes = [[NSFileManager defaultManager] attributesOfItemAtPath:draggedPath error:nil]; 

      if (draggedAttributes == nil) 
       continue; 

      // the NSFileWrapper allows access to the absolute file via NSFileSystemFileNumber 
      // put the path and the inode (returned as an NSNumber) into a NSMutableDictionary 

      NSNumber *draggedInode = [draggedAttributes objectForKey:NSFileSystemFileNumber]; 

      [draggedFiles setObject:draggedPath forKey:draggedInode]; 
     } 

    } 

    return [super draggingEntered:sender]; 
} 

Un problema con mi solución, que no afecta mi solicitud, es que varios archivos arrastrados a la vista (ya sea por separado o en conjunto) sólo serán indexados, que son enlaces fijos con el mismo archivo, como el último nombre de ruta agregado al diccionario que comparte el inodo. Dependiendo de cómo los nombres de ruta son utilizados por su aplicación, esto podría ser un problema.

+0

Genial, pero fastidioso. Al investigar esto, asumí que arrastrar a'Entered era hacia donde me dirigía, pero aún no había puesto el código. Probaré tu ejemplo en los próximos días y te lo haré saber. ¡Gracias! –

+0

Parece que esta es la única forma de hacerlo. Gracias por los ejemplos del código: me está llevando a donde tengo que ir. Aceptado esta respuesta. –

Cuestiones relacionadas