Forum

Author Topic: Custom batch process in menu on startup  (Read 7656 times)

smcmurray

  • Newbie
  • *
  • Posts: 15
  • Registered Mine Surveyor
    • View Profile
Custom batch process in menu on startup
« on: September 22, 2017, 06:09:45 AM »
I have a two part custom batch process that I want to appear in my menu structure on startup so that I can use it to process my UAV data - how would I do this ?

Do I need a python script to be able to do this or would it make it easier ?

Thanks in advance
Steve

SAV

  • Hero Member
  • *****
  • Posts: 710
    • View Profile
Re: Custom batch process in menu on startup
« Reply #1 on: September 22, 2017, 11:37:04 AM »
Hi smcmurray,

For Windows, you need to place your Python Script (*.py file) in this folder:

C:\Users\[YOUR_USER_NAME}\AppData\Local\Agisoft\PhotoScan Pro\scripts

Also make sure that you use this syntax in your Python Script:

Code: [Select]
import PhotoScan

def give_me_a_name():
    doc = PhotoScan.app.document
    chunk = doc.chunk

    [place your code here]


PhotoScan.app.addMenuItem("Custom/Give me a name", give_me_a_name)

When you start PhotoScan, you should now see a Custom menu which allows you to run your script.

Let me know if it worked for you.

Regards,
SAV

smcmurray

  • Newbie
  • *
  • Posts: 15
  • Registered Mine Surveyor
    • View Profile
Re: Custom batch process in menu on startup
« Reply #2 on: September 29, 2017, 04:26:36 AM »
Thanks SAV - I have the batch process in the .xml format that agisoft saves the batch process in - can I link this or do I need to put the process into a python script ?

Thanks in advance mate

Steve

smcmurray

  • Newbie
  • *
  • Posts: 15
  • Registered Mine Surveyor
    • View Profile
Re: Custom batch process in menu on startup
« Reply #3 on: September 29, 2017, 05:52:45 AM »
Hi SAV

I have put that code in :
Code: [Select]
import PhotoScan
import os,re,sys

def give_me_a_name():
    doc = PhotoScan.app.document
    chunk = doc.chunk

# get the photo (.JPG) list in specified folder
def getPhotoList(root_path, photoList):
pattern = '.JPG$'
for root, dirs, files in os.walk(root_path):
for name in files:
if re.search(pattern,name):
cur_path = os.path.join(root, name)
#print (cur_path)
photoList.append(cur_path)

def photoscanProcess(root_path):
#PhotoScan.app.messageBox('hello world! \n')
PhotoScan.app.console.clear()

## construct the document class
doc = PhotoScan.app.document

## save project
#doc.open("D:\03_UAV\QCNH\170906_QCNH_Q_Rom\practise.psx")
psxfile = root_path + 'practise.psx'
doc.save( psxfile )
print ('>> Saved to: ' + psxfile)

## point to current chunk
#chunk = doc.chunk

## add a new chunk
chunk = doc.addChunk()

## set coordinate system
# - PhotoScan.CoordinateSystem("EPSG::4612") -->  JGD2000
chunk.crs = PhotoScan.CoordinateSystem("EPSG::4612")

################################################################################################
### get photo list ###
photoList = []
getPhotoList(root_path, photoList)
#print (photoList)

################################################################################################
### add photos ###
# addPhotos(filenames[, progress])
# - filenames(list of string) – A list of file paths.
chunk.addPhotos(photoList)

################################################################################################
### align photos ###
## Perform image matching for the chunk frame.
# matchPhotos(accuracy=HighAccuracy, preselection=NoPreselection, filter_mask=False, keypoint_limit=40000, tiepoint_limit=4000[, progress])
# - Alignment accuracy in [HighestAccuracy, HighAccuracy, MediumAccuracy, LowAccuracy, LowestAccuracy]
# - Image pair preselection in [ReferencePreselection, GenericPreselection, NoPreselection]
chunk.matchPhotos(accuracy=PhotoScan.LowAccuracy, preselection=PhotoScan.ReferencePreselection, filter_mask=False, keypoint_limit=0, tiepoint_limit=0)
chunk.alignCameras()

################################################################################################
### build dense cloud ###
## Generate depth maps for the chunk.
# buildDenseCloud(quality=MediumQuality, filter=AggressiveFiltering[, cameras], keep_depth=False, reuse_depth=False[, progress])
# - Dense point cloud quality in [UltraQuality, HighQuality, MediumQuality, LowQuality, LowestQuality]
# - Depth filtering mode in [AggressiveFiltering, ModerateFiltering, MildFiltering, NoFiltering]
chunk.buildDenseCloud(quality=PhotoScan.LowQuality, filter=PhotoScan.AggressiveFiltering)

################################################################################################
### build mesh ###
## Generate model for the chunk frame.
# buildModel(surface=Arbitrary, interpolation=EnabledInterpolation, face_count=MediumFaceCount[, source ][, classes][, progress])
# - Surface type in [Arbitrary, HeightField]
# - Interpolation mode in [EnabledInterpolation, DisabledInterpolation, Extrapolated]
# - Face count in [HighFaceCount, MediumFaceCount, LowFaceCount]
# - Data source in [PointCloudData, DenseCloudData, ModelData, ElevationData]
chunk.buildModel(surface=PhotoScan.HeightField, interpolation=PhotoScan.EnabledInterpolation, face_count=PhotoScan.HighFaceCount)

################################################################################################
### build texture (optional) ###
## Generate uv mapping for the model.
# buildUV(mapping=GenericMapping, count=1[, camera ][, progress])
# - UV mapping mode in [GenericMapping, OrthophotoMapping, AdaptiveOrthophotoMapping, SphericalMapping, CameraMapping]
#chunk.buildUV(mapping=PhotoScan.AdaptiveOrthophotoMapping)
## Generate texture for the chunk.
# buildTexture(blending=MosaicBlending, color_correction=False, size=2048[, cameras][, progress])
# - Blending mode in [AverageBlending, MosaicBlending, MinBlending, MaxBlending, DisabledBlending]
#chunk.buildTexture(blending=PhotoScan.MosaicBlending, color_correction=True, size=30000)

################################################################################################
## save the project before build the DEM and Ortho images
doc.save()

################################################################################################
### build DEM (before build dem, you need to save the project into psx) ###
## Build elevation model for the chunk.
# buildDem(source=DenseCloudData, interpolation=EnabledInterpolation[, projection ][, region ][, classes][, progress])
# - Data source in [PointCloudData, DenseCloudData, ModelData, ElevationData]
chunk.buildDem(source=PhotoScan.DenseCloudData, interpolation=PhotoScan.EnabledInterpolation, projection=chunk.crs)

################################################################################################
## Build orthomosaic for the chunk.
# buildOrthomosaic(surface=ElevationData, blending=MosaicBlending, color_correction=False[, projection ][, region ][, dx ][, dy ][, progress])
# - Data source in [PointCloudData, DenseCloudData, ModelData, ElevationData]
# - Blending mode in [AverageBlending, MosaicBlending, MinBlending, MaxBlending, DisabledBlending]
chunk.buildOrthomosaic(surface=PhotoScan.ModelData, blending=PhotoScan.MosaicBlending, color_correction=True, projection=chunk.crs)

################################################################################################
## auto classify ground points (optional)
#chunk.dense_cloud.classifyGroundPoints()
#chunk.buildDem(source=PhotoScan.DenseCloudData, classes=[2])

################################################################################################
doc.save()

PhotoScan.app.addMenuItem("Custom/Batch Process", give_me_a_name)

# main
folder = "D:/03_UAV/QCNH/170906_QCNH_Q_Rom"
photoscanProcess(folder)

but I get the following reply :
2017-09-29 12:43:02 MAVinci Plugin: created with MAVinci Desktop for Win (SN: 81dc6ff3d850094195d55a1eea37cbfb, Steve McMurray, Thiess Pty Ltd, smcmurray@thiess.com.au) 6.0.b53776 at 13:16:35 06.09.2017 exported for PhotoScan VERSION:1.2.6 build:2834 resourceFile:MAVinciLib_1-2
2017-09-29 12:43:02 PhotoscanVersion: 1.2.6
2017-09-29 12:43:02 MAVinci Plugin ready loaded
2017-09-29 12:43:02 Traceback (most recent call last):
2017-09-29 12:43:02   File "C:/Users/smcmurray/AppData/Local/Agisoft/PhotoScan Pro/scripts/Agisoft Batch Process 1.py", line 124, in <module>
2017-09-29 12:43:02     photoscanProcess(folder)
2017-09-29 12:43:02   File "C:/Users/smcmurray/AppData/Local/Agisoft/PhotoScan Pro/scripts/Agisoft Batch Process 1.py", line 31, in photoscanProcess
2017-09-29 12:43:02     doc.save( psxfile )
2017-09-29 12:43:02 AttributeError: 'NoneType' object has no attribute 'save'

Any ideas ?

Steve

Alexey Pasumansky

  • Agisoft Technical Support
  • Hero Member
  • *****
  • Posts: 15282
    • View Profile
Re: Custom batch process in menu on startup
« Reply #4 on: September 29, 2017, 06:20:32 PM »
Hello Steve,

In the version 1.2 it was not possible to use .save() function with PhotoScan.app.document.

But you can use assignment doc = PhotoScan.Document() instead.
Best regards,
Alexey Pasumansky,
Agisoft LLC

magic

  • Jr. Member
  • **
  • Posts: 53
    • View Profile
Re: Custom batch process in menu on startup
« Reply #5 on: November 28, 2017, 02:15:15 PM »
Hello

Anybody can help me maybe here, i have a problem with Custom button , iv added it to  C:Users/......./script and my button vbeen created in my photoscan menu, but i cant open it when i go to >> Custom>>(myscript)Selectioner desactiver , there is no callback from ... nothing happens,  my python skill are low maybe someone will help :

there is my code
Code: [Select]
import os
import PhotoScan
from tkinter import*

def selec():
    doc = PhotoScan.app.document
    chunk = doc.chunk

def center_window(width=500, height=400):
    # hoteur et largeur notre fenetre
    screen_width = root.winfo_screenwidth()
    screen_height = root.winfo_screenheight()

    # calcule positionement notre fenetre sur ecran
    x = (screen_width/2) - (width/2)
    y = (screen_height/2) - (height/2)
    root.geometry('%dx%d+%d+%d' % (width, height, x, y))





root = Tk()
center_window(500, 400)
root.title('selection images')

###### premiere boutton - selection les images activer
def callback():
    chunk = PhotoScan.app.document.chunk
    for camera in chunk.cameras:
        if camera.enabled:
            camera.selected = True
        else:
            camera.selected = False

but = Button(root,bg='yellow',width =20, height =2, bd =2, relief =SOLID, text='selection active', command=callback)

but.pack()

######## partie liaison avec photoscan
PhotoScan.app.addMenuItem("Custom/Selection desactiver", selec)
root.mainloop()

iv tried few combination and cant get positive results im stuck with it since friday, if someone of u know why that dsnt work i will glad 4 a answer.
And would like to ask u why this custom window starting together with photoscan, if i will add 10 scripts (custom windows) I will have to closed them all before i will be able to use photoscan